/** Handles size after put. */
  private void onPut() {
    cnt.incrementAndGet();

    int c;

    while ((c = cnt.get()) > max) {
      // Decrement count.
      if (cnt.compareAndSet(c, c - 1)) {
        try {
          K key = firstEntry().getKey();

          V val;

          // Make sure that an element is removed.
          while ((val = super.remove(firstEntry().getKey())) == null) {
            // No-op.
          }

          assert val != null;

          GridInClosure2<K, V> lsnr = this.lsnr;

          // Listener notification.
          if (lsnr != null) lsnr.apply(key, val);
        } catch (NoSuchElementException e1) {
          e1.printStackTrace(); // Should never happen.

          assert false : "Internal error in grid bounded ordered set.";
        }
      }
    }
  }
Esempio n. 2
0
  @Test
  public void testPublishLast() throws InterruptedException {
    final AtomicInteger count = new AtomicInteger();
    ConnectableObservable<String> connectable =
        Observable.<String>create(
                observer -> {
                  observer.onSubscribe(EmptySubscription.INSTANCE);
                  count.incrementAndGet();
                  new Thread(
                          () -> {
                            observer.onNext("first");
                            observer.onNext("last");
                            observer.onComplete();
                          })
                      .start();
                })
            .takeLast(1)
            .publish();

    // subscribe once
    final CountDownLatch latch = new CountDownLatch(1);
    connectable.subscribe(
        value -> {
          assertEquals("last", value);
          latch.countDown();
        });

    // subscribe twice
    connectable.subscribe();

    Disposable subscription = connectable.connect();
    assertTrue(latch.await(1000, TimeUnit.MILLISECONDS));
    assertEquals(1, count.get());
    subscription.dispose();
  }
Esempio n. 3
0
  public void newCharacter(CharacterEvent ce) {
    int oldChar2type;

    // Previous character not typed correctly - 1 point penalty
    if (ce.source == generator.get()) {
      oldChar2type = char2type.getAndSet(ce.character); // 接收随机字母

      if (oldChar2type != -1) {
        score.decrementAndGet();
        setScore();
      }
    }
    // If character is extraneous - 1 point penalty
    // If character does not match - 1 point penalty
    else if (ce.source == typist.get()) {
      // 在此有个假设:即正在使用的该变量值不会被变更且程序代码完成时也是如此
      // 所有已经被我们设定的具有特定值的变量就应当是那个值。
      while (true) {
        oldChar2type = char2type.get(); // 获取上次已接收到的随机字母

        if (oldChar2type != ce.character) { // ce.character是用户输入的字母,现在作比较
          score.decrementAndGet();
          break;
        } else if (char2type.compareAndSet(oldChar2type, -1)) {
          score.incrementAndGet();
          break;
        }
      }

      setScore();
    }
  }
  /** {@inheritDoc} */
  @Override
  protected Collection<E> dequeue0(int cnt) {
    WindowHolder tup = ref.get();

    AtomicInteger size = tup.size();
    Collection<T> evts = tup.collection();

    Collection<E> resCol = new ArrayList<>(cnt);

    while (true) {
      int curSize = size.get();

      if (curSize > 0) {
        if (size.compareAndSet(curSize, curSize - 1)) {
          E res = pollInternal(evts, tup.set());

          if (res != null) {
            resCol.add(res);

            if (resCol.size() >= cnt) return resCol;
          } else {
            size.incrementAndGet();

            return resCol;
          }
        }
      } else return resCol;
    }
  }
  /**
   * Poll evicted internal implementation.
   *
   * @return Evicted element.
   */
  @Nullable
  private E pollEvictedInternal() {
    WindowHolder tup = ref.get();

    AtomicInteger size = tup.size();

    while (true) {
      int curSize = size.get();

      if (curSize > maxSize) {
        if (size.compareAndSet(curSize, curSize - 1)) {
          E evt = pollInternal(tup.collection(), tup.set());

          if (evt != null) return evt;
          else {
            // No actual events in queue, it means that other thread is just adding event.
            // return null as it is a concurrent add call.
            size.incrementAndGet();

            return null;
          }
        }
      } else return null;
    }
  }
Esempio n. 6
0
  @Test(timeout = 20000)
  public void testOnBackpressureDropWithAction() {
    for (int i = 0; i < 100; i++) {
      final AtomicInteger emitCount = new AtomicInteger();
      final AtomicInteger dropCount = new AtomicInteger();
      final AtomicInteger passCount = new AtomicInteger();
      final int NUM =
          Observable.bufferSize() * 3; // > 1 so that take doesn't prevent buffer overflow
      TestSubscriber<Integer> ts = new TestSubscriber<>();

      firehose(emitCount)
          .onBackpressureDrop(v -> dropCount.incrementAndGet())
          .doOnNext(v -> passCount.incrementAndGet())
          .observeOn(Schedulers.computation())
          .map(SLOW_PASS_THRU)
          .take(NUM)
          .subscribe(ts);

      ts.awaitTerminalEvent();
      ts.assertNoErrors();

      List<Integer> onNextEvents = ts.values();
      Integer lastEvent = onNextEvents.get(NUM - 1);
      System.out.println(
          testName.getMethodName()
              + " => Received: "
              + onNextEvents.size()
              + " Passed: "
              + passCount.get()
              + " Dropped: "
              + dropCount.get()
              + "  Emitted: "
              + emitCount.get()
              + " Last value: "
              + lastEvent);
      assertEquals(NUM, onNextEvents.size());
      // in reality, NUM < passCount
      assertTrue(NUM <= passCount.get());
      // it drop, so we should get some number far higher than what would have sequentially
      // incremented
      assertTrue(NUM - 1 <= lastEvent.intValue());
      assertTrue(0 < dropCount.get());
      assertEquals(emitCount.get(), passCount.get() + dropCount.get());
    }
  }
Esempio n. 7
0
 @Test
 public void testTakeWhileToList() {
   final int expectedCount = 3;
   final AtomicInteger count = new AtomicInteger();
   for (int i = 0; i < expectedCount; i++) {
     Observable.just(Boolean.TRUE, Boolean.FALSE)
         .takeWhile(v -> v)
         .toList()
         .doOnNext(booleans -> count.incrementAndGet())
         .subscribe();
   }
   assertEquals(expectedCount, count.get());
 }
 public void run() {
   done.countDown();
   remaining.incrementAndGet();
   int n;
   while (!Thread.interrupted() && (n = remaining.get()) > 0 && done.getCount() > 0) {
     if (remaining.compareAndSet(n, n - 1)) {
       try {
         pool.execute(this);
       } catch (RuntimeException ex) {
         System.out.print("*");
         while (done.getCount() > 0) done.countDown();
         return;
       }
     }
   }
 }
Esempio n. 9
0
    @Override
    public void request(long n) {
      if (SubscriptionHelper.validateRequest(n)) {
        return;
      }
      if (compareAndSet(false, true)) {
        int i = 0;
        final Subscriber<? super Integer> a = s;
        final AtomicInteger c = counter;

        while (!cancelled) {
          a.onNext(i++);
          c.incrementAndGet();
        }
        System.out.println("unsubscribed after: " + i);
      }
    }
Esempio n. 10
0
  @Test
  public void testCacheWithCapacity() throws InterruptedException {
    final AtomicInteger counter = new AtomicInteger();
    Observable<String> o =
        Observable.<String>create(
                observer -> {
                  observer.onSubscribe(EmptySubscription.INSTANCE);
                  new Thread(
                          () -> {
                            counter.incrementAndGet();
                            observer.onNext("one");
                            observer.onComplete();
                          })
                      .start();
                })
            .cache(1);

    // we then expect the following 2 subscriptions to get that same value
    final CountDownLatch latch = new CountDownLatch(2);

    // subscribe once
    o.subscribe(
        v -> {
          assertEquals("one", v);
          latch.countDown();
        });

    // subscribe again
    o.subscribe(
        v -> {
          assertEquals("one", v);
          latch.countDown();
        });

    if (!latch.await(1000, TimeUnit.MILLISECONDS)) {
      fail("subscriptions did not receive values");
    }
    assertEquals(1, counter.get());
  }
Esempio n. 11
0
  @Test(timeout = 10000)
  public void testOnBackpressureDropSynchronousWithAction() {
    for (int i = 0; i < 100; i++) {
      final AtomicInteger dropCount = new AtomicInteger();
      int NUM =
          (int) (Observable.bufferSize() * 1.1); // > 1 so that take doesn't prevent buffer overflow
      AtomicInteger c = new AtomicInteger();
      TestSubscriber<Integer> ts = new TestSubscriber<>();
      firehose(c)
          .onBackpressureDrop(j -> dropCount.incrementAndGet())
          .map(SLOW_PASS_THRU)
          .take(NUM)
          .subscribe(ts);
      ts.awaitTerminalEvent();
      ts.assertNoErrors();

      List<Integer> onNextEvents = ts.values();
      assertEquals(NUM, onNextEvents.size());

      Integer lastEvent = onNextEvents.get(NUM - 1);

      System.out.println(
          "testOnBackpressureDrop => Received: "
              + onNextEvents.size()
              + " Dropped: "
              + dropCount.get()
              + "  Emitted: "
              + c.get()
              + " Last value: "
              + lastEvent);
      // it drop, so we should get some number far higher than what would have sequentially
      // incremented
      assertTrue(NUM - 1 <= lastEvent.intValue());
      // no drop in synchronous mode
      assertEquals(0, dropCount.get());
      assertEquals(c.get(), onNextEvents.size());
    }
  }
Esempio n. 12
0
  private DarkBotMCSpambot(
      DarkBot darkBot,
      String server,
      String username,
      String password,
      String sessionId,
      String loginProxy,
      String proxy,
      String owner) {
    synchronized (bots) {
      bots.add(this);
      // slotsTaken.incrementAndGet();
      synchronized (slotsTaken) {
        slotsTaken.notifyAll();
      }
    }
    MinecraftBotData.Builder builder = MinecraftBotData.builder();
    // botData.nickname = "";
    // for(int i = 0; i < 10; i++)
    // botData.nickname += alphas[random.nextInt(alphas.length)];
    if (proxy != null && !proxy.isEmpty()) {
      int port = 80;
      ProxyType type = ProxyType.SOCKS;
      if (proxy.contains(":")) {
        String[] parts = proxy.split(":");
        proxy = parts[0];
        port = Integer.parseInt(parts[1]);
        if (parts.length > 2) type = ProxyType.values()[Integer.parseInt(parts[2]) - 1];
      }
      builder.withSocksProxy(new ProxyData(proxy, port, type));
      this.proxy = new Proxy(Proxy.Type.SOCKS, new InetSocketAddress(proxy, port));
    }
    if (loginProxy != null && !loginProxy.isEmpty()) {
      int port = 80;
      if (loginProxy.contains(":")) {
        String[] parts = loginProxy.split(":");
        loginProxy = parts[0];
        port = Integer.parseInt(parts[1]);
      }
      builder.withHttpProxy(new ProxyData(loginProxy, port, ProxyType.HTTP));
      this.loginProxy = new Proxy(Proxy.Type.HTTP, new InetSocketAddress(loginProxy, port));
    }
    builder.withUsername(username);
    if (sessionId != null) builder.withSessionId(sessionId);
    else builder.withPassword(password);
    if (server != null && !server.isEmpty()) {
      int port = 25565;
      if (server.contains(":")) {
        String[] parts = server.split(":");
        server = parts[0];
        port = Integer.parseInt(parts[1]);
      }
      builder.withServer(server).withPort(port);
    } else throw new IllegalArgumentException("Unknown server!");

    this.owner = owner;
    MinecraftBotData botData = builder.build();
    System.setProperty("socksProxyHost", "");
    System.setProperty("socksProxyPort", "");
    System.out.println("[" + username + "] Connecting...");
    bot = new MinecraftBot(darkBot, botData);
    bot.setMovementDisabled(true);
    connectionHandler = bot.getConnectionHandler();
    Session session = bot.getSession();
    // System.gc();
    System.out.println("[" + username + "] Done! (" + amountJoined.incrementAndGet() + ")");
    bot.getEventManager().registerListener(this);
    bot.getGameHandler().registerListener(this);

    long lastShoutTime = System.currentTimeMillis();
    while (bot.isConnected()) {
      if (die) {
        connectionHandler.sendPacket(new Packet255KickDisconnect("Goodbye"));
        return;
      }
      try {
        Thread.sleep(3000 + random.nextInt(1000));
      } catch (InterruptedException exception) {
        exception.printStackTrace();
      }
      if (!bot.hasSpawned()) continue;
      connectionHandler.sendPacket(new Packet0KeepAlive(random.nextInt()));
      if (spamMessage == null || !canSpam) continue;
      String message = spamMessage;
      if (message.contains("%skill")) message = message.replace("%skill", skills[nextSkill++]);
      if (nextSkill >= skills.length) nextSkill = 0;
      if (message.contains("%bot")) {
        synchronized (bots) {
          message =
              message.replace(
                  "%bot",
                  bots.get(nextBot > bots.size() ? (nextBot = 0) * 0 : nextBot++)
                      .bot
                      .getSession()
                      .getUsername());
        }
      }
      if (message.contains("%spamlist"))
        message = message.replace("%spamlist", spamList[nextSpamList++]);
      if (nextSpamList >= spamList.length) nextSpamList = 0;
      if (message.contains("%rnd")) {
        int length = 1;
        int index = message.indexOf("%rnd") + "%rnd".length();
        int lastIndex;
        for (lastIndex = index; lastIndex < message.length(); lastIndex++)
          if (Character.isDigit(message.charAt(lastIndex))) lastIndex++;
          else break;
        if (lastIndex > message.length()) lastIndex--;
        try {
          System.out.println(index + "," + lastIndex + "," + message.length());
          length = Integer.parseInt(message.substring(index, lastIndex));
        } catch (Exception exception) {
        }

        String randomChars = "";
        for (int i = 0; i < length; i++) randomChars += alphas[random.nextInt(alphas.length)];
        message = message.replace("%rnd", randomChars);
      }
      if (message.contains("%msg"))
        message = "/msg " + msgChars[nextMsgChar++] + " " + message.replace("%msg", "");
      if (message.contains("%ernd")) {
        message = message.replace("%ernd", "");
        int extraMessageLength = 15 + random.nextInt(6);
        message = message.substring(0, Math.min(100 - extraMessageLength, message.length())) + " [";
        extraMessageLength -= 3;
        for (int i = 0; i < extraMessageLength; i++)
          message += alphas[random.nextInt(alphas.length)];
        message += "]";
      } else message = message.substring(0, Math.min(100, message.length()));
      connectionHandler.sendPacket(new Packet3Chat(message));
    }
    synchronized (bots) {
      bots.remove(this);
    }
    amountJoined.decrementAndGet();
    slotsTaken.decrementAndGet();
    synchronized (slotsTaken) {
      slotsTaken.notifyAll();
    }
  }
Esempio n. 13
0
 public Thread newThread(Runnable r) {
   numCreated.incrementAndGet();
   return factory.newThread(r);
 }
Esempio n. 14
0
/**
 * Abstract node type.
 *
 * @author BaseX Team 2005-15, BSD License
 * @author Christian Gruen
 */
public abstract class ANode extends Item {
  /** Node Types. */
  private static final NodeType[] TYPES = {
    NodeType.DOC, NodeType.ELM, NodeType.TXT, NodeType.ATT, NodeType.COM, NodeType.PI
  };
  /** Static node counter. */
  // [CG] XQuery, node id: move to query context to reduce chance of overflow, or
  // move to FNode to reduce memory usage of DBNode instances
  private static final AtomicInteger ID = new AtomicInteger();
  /** Unique node id. */
  public final int id = ID.incrementAndGet();

  /** Cached string value. */
  byte[] value;
  /** Parent node. */
  ANode parent;

  /**
   * Constructor.
   *
   * @param type item type
   */
  ANode(final NodeType type) {
    super(type);
  }

  @Override
  public final boolean bool(final InputInfo ii) {
    return true;
  }

  @Override
  public final byte[] string(final InputInfo ii) {
    return string();
  }

  /**
   * Returns the string value.
   *
   * @return string value
   */
  public abstract byte[] string();

  @Override
  public final boolean eq(
      final Item it, final Collation coll, final StaticContext sc, final InputInfo ii)
      throws QueryException {
    return it.type.isUntyped()
        ? coll == null
            ? Token.eq(string(), it.string(ii))
            : coll.compare(string(), it.string(ii)) == 0
        : it.eq(this, coll, sc, ii);
  }

  @Override
  public boolean sameKey(final Item it, final InputInfo ii) throws QueryException {
    return it.type.isStringOrUntyped() && eq(it, null, null, ii);
  }

  @Override
  public final int diff(final Item it, final Collation coll, final InputInfo ii)
      throws QueryException {
    return it.type.isUntyped()
        ? coll == null ? Token.diff(string(), it.string(ii)) : coll.compare(string(), it.string(ii))
        : -it.diff(this, coll, ii);
  }

  @Override
  public final Item atomItem(final InputInfo ii) {
    return type == NodeType.PI || type == NodeType.COM ? Str.get(string()) : new Atm(string());
  }

  /**
   * Creates a copy of this node.
   *
   * @return copy
   */
  public abstract ANode copy();

  /**
   * Returns a deep copy of the node.
   *
   * @param opts main options
   * @return node copy
   */
  public abstract ANode deepCopy(final MainOptions opts);

  /**
   * Returns a database node representation of the node.
   *
   * @param opts main options
   * @return database node
   */
  public DBNode dbCopy(final MainOptions opts) {
    final MemData md = new MemData(opts);
    new DataBuilder(md).build(this);
    return new DBNode(md);
  }

  /**
   * Returns the name of the node, composed of an optional prefix and the local name. This function
   * must only be called for element and attribute nodes. It is more efficient than calling {@link
   * #qname}, as no {@link QNm} instance is created.
   *
   * @return name
   */
  public byte[] name() {
    return null;
  }

  /**
   * Returns the QName of the node. This function must only be called for elements, attributes and
   * pi's.
   *
   * @return name
   */
  public QNm qname() {
    return null;
  }

  /**
   * Updates the specified with the information of the current node. This is more efficient than
   * calling {@link #qname}, as an existing {@link QNm} instance is reused. This function must only
   * be called for elements, attributes and pi's.
   *
   * @param nm temporary qname
   * @return name
   */
  public abstract QNm qname(final QNm nm);

  /**
   * Minimizes the memory consumption of the node.
   *
   * @return self reference
   */
  public ANode optimize() {
    return this;
  }

  /**
   * Returns all namespaces defined for the nodes. Overwritten by {@link FElem} and {@link DBNode}.
   *
   * @return namespace array
   */
  public Atts namespaces() {
    return null;
  }

  /**
   * Returns a copy of the namespace hierarchy.
   *
   * @param sc static context (can be {@code null})
   * @return namespaces
   */
  public final Atts nsScope(final StaticContext sc) {
    final Atts ns = new Atts();
    ANode node = this;
    do {
      final Atts nsp = node.namespaces();
      if (nsp != null) {
        for (int a = nsp.size() - 1; a >= 0; a--) {
          final byte[] key = nsp.name(a);
          if (!ns.contains(key)) ns.add(key, nsp.value(a));
        }
      }
      node = node.parent();
    } while (node != null && node.type == NodeType.ELM);
    if (sc != null) sc.ns.inScope(ns);
    return ns;
  }

  /**
   * Recursively finds the uri for the specified prefix.
   *
   * @param pref prefix
   * @return uri
   */
  public final byte[] uri(final byte[] pref) {
    final Atts at = namespaces();
    if (at != null) {
      final byte[] s = at.value(pref);
      if (s != null) return s;
      final ANode n = parent();
      if (n != null) return n.uri(pref);
    }
    return pref.length == 0 ? Token.EMPTY : null;
  }

  /**
   * Returns the base URI of the node.
   *
   * @return base URI
   */
  public byte[] baseURI() {
    return Token.EMPTY;
  }

  /**
   * Checks if two nodes are identical.
   *
   * @param node node to be compared
   * @return result of check
   */
  public abstract boolean is(final ANode node);

  /**
   * Checks the document order of two nodes.
   *
   * @param node node to be compared
   * @return {@code 0} if the nodes are identical, or {@code 1}/{@code -1} if the node appears
   *     after/before the argument
   */
  public abstract int diff(final ANode node);

  /**
   * Compares two nodes for their unique order.
   *
   * @param node1 first node
   * @param node2 node to be compared
   * @return {@code 0} if the nodes are identical, or {@code 1}/{@code -1} if the first node appears
   *     after/before the second
   */
  static int diff(final ANode node1, final ANode node2) {
    // cache parents of first node
    final ANodeList nl = new ANodeList();
    for (ANode n = node1; n != null; n = n.parent()) {
      if (n == node2) return 1;
      nl.add(n);
    }
    // find lowest common ancestor
    ANode c2 = node2;
    LOOP:
    for (ANode n = node2; (n = n.parent()) != null; ) {
      final int is = nl.size();
      for (int i = 1; i < is; i++) {
        if (n == node1) return -1;
        if (!nl.get(i).is(n)) continue;
        // check which node appears as first LCA child
        final ANode c1 = nl.get(i - 1);
        final BasicNodeIter ir = n.children();
        for (ANode c; (c = ir.next()) != null; ) {
          if (c.is(c1)) return -1;
          if (c.is(c2)) return 1;
        }
        break LOOP;
      }
      c2 = n;
    }
    // subtraction is used instead of comparison to support overflow of node id
    return node1.id - node2.id < 0 ? -1 : 1;
  }

  /**
   * Returns a final node representation. This method is called by the step expressions, before it
   * is passed on as result.
   *
   * @return node
   */
  public ANode finish() {
    return this;
  }

  /**
   * Returns the root of a node (the topmost ancestor without parent node).
   *
   * @return root node
   */
  public final ANode root() {
    final ANode p = parent();
    return p == null ? this : p.root();
  }

  /**
   * Returns the parent node.
   *
   * @return parent node
   */
  public abstract ANode parent();

  /**
   * Sets the parent node.
   *
   * @param par parent node
   * @return self reference
   */
  protected abstract ANode parent(final ANode par);

  /**
   * Returns true if the node has children.
   *
   * @return result of test
   */
  public abstract boolean hasChildren();

  /**
   * Returns the value of the specified attribute or {@code null}.
   *
   * @param name attribute to be found
   * @return attribute value
   */
  public byte[] attribute(final String name) {
    return attribute(new QNm(name));
  }

  /**
   * Returns the value of the specified attribute or {@code null}.
   *
   * @param name attribute to be found
   * @return attribute value
   */
  public byte[] attribute(final byte[] name) {
    return attribute(new QNm(name));
  }

  /**
   * Returns the value of the specified attribute or {@code null}.
   *
   * @param name attribute to be found
   * @return attribute value
   */
  public byte[] attribute(final QNm name) {
    final BasicNodeIter iter = attributes();
    while (true) {
      final ANode node = iter.next();
      if (node == null) return null;
      if (node.qname().eq(name)) return node.string();
    }
  }

  /**
   * Returns an ancestor axis iterator. If nodes returned are to be further used, they must be
   * finalized via {@link ANode#finish()}.
   *
   * @return iterator
   */
  public abstract BasicNodeIter ancestor();

  /**
   * Returns an ancestor-or-self axis iterator. If nodes returned are to be further used, they must
   * be finalized via {@link ANode#finish()}.
   *
   * @return iterator
   */
  public abstract BasicNodeIter ancestorOrSelf();

  /**
   * Returns an attribute axis iterator. If nodes returned are to be further used, they must be
   * finalized via {@link ANode#finish()}.
   *
   * @return iterator
   */
  public abstract BasicNodeIter attributes();

  /**
   * Returns a child axis iterator. If nodes returned are to be further used, they must be finalized
   * via {@link ANode#finish()}.
   *
   * @return iterator
   */
  public abstract BasicNodeIter children();

  /**
   * Returns a descendant axis iterator. If nodes returned are to be further used, they must be
   * finalized via {@link ANode#finish()}.
   *
   * @return iterator
   */
  public abstract BasicNodeIter descendant();

  /**
   * Returns a descendant-or-self axis iterator. If nodes returned are to be further used, they must
   * be finalized via {@link ANode#finish()}.
   *
   * @return iterator
   */
  public abstract BasicNodeIter descendantOrSelf();

  /**
   * Returns a following axis iterator. If nodes returned are to be further used, they must be
   * finalized via {@link ANode#finish()}.
   *
   * @return iterator
   */
  public abstract BasicNodeIter following();

  /**
   * Returns a following-sibling axis iterator. If nodes returned are to be further used, they must
   * be finalized via {@link ANode#finish()}.
   *
   * @return iterator
   */
  public abstract BasicNodeIter followingSibling();

  /**
   * Returns a parent axis iterator. If nodes returned are to be further used, they must be
   * finalized via {@link ANode#finish()}.
   *
   * @return iterator
   */
  public abstract BasicNodeIter parentIter();

  /**
   * Returns a preceding axis iterator. If nodes returned are to be further used, they must be
   * finalized via {@link ANode#finish()}.
   *
   * @return iterator
   */
  public final BasicNodeIter preceding() {
    return new BasicNodeIter() {
      /** Iterator. */
      private BasicNodeIter iter;

      @Override
      public ANode next() {
        if (iter == null) {
          final ANodeList list = new ANodeList();
          ANode n = ANode.this;
          ANode p = n.parent();
          while (p != null) {
            if (n.type != NodeType.ATT) {
              final ANodeList tmp = new ANodeList();
              final BasicNodeIter ir = p.children();
              for (ANode c; (c = ir.next()) != null && !c.is(n); ) {
                tmp.add(c.finish());
                addDesc(c.children(), tmp);
              }
              for (int t = tmp.size() - 1; t >= 0; t--) list.add(tmp.get(t));
            }
            n = p;
            p = p.parent();
          }
          iter = list.iter();
        }
        return iter.next();
      }
    };
  }

  /**
   * Returns a preceding-sibling axis iterator. If nodes returned are to be further used, they must
   * be finalized via {@link ANode#finish()}.
   *
   * @return iterator
   */
  public final BasicNodeIter precedingSibling() {
    return new BasicNodeIter() {
      /** Child nodes. */
      private BasicNodeIter iter;
      /** Counter. */
      private int i;

      @Override
      public ANode next() {
        if (iter == null) {
          if (type == NodeType.ATT) return null;
          final ANode r = parent();
          if (r == null) return null;

          final ANodeList list = new ANodeList();
          final BasicNodeIter ir = r.children();
          for (ANode n; (n = ir.next()) != null && !n.is(ANode.this); ) list.add(n.finish());
          i = list.size();
          iter = list.iter();
        }
        return i > 0 ? iter.get(--i) : null;
      }
    };
  }

  /**
   * Returns an self axis iterator.
   *
   * @return iterator
   */
  public final BasicNodeIter self() {
    return new BasicNodeIter() {
      /** Flag. */
      private boolean all;

      @Override
      public ANode next() {
        if (all) return null;
        all = true;
        return ANode.this;
      }
    };
  }

  /**
   * Adds children of a sub node.
   *
   * @param ch child nodes
   * @param nb node cache
   */
  static void addDesc(final BasicNodeIter ch, final ANodeList nb) {
    for (ANode n; (n = ch.next()) != null; ) {
      nb.add(n.finish());
      addDesc(n.children(), nb);
    }
  }

  /**
   * Returns a database kind for the specified node type.
   *
   * @return node kind
   */
  public int kind() {
    return kind(nodeType());
  }

  /**
   * Returns a database kind for the specified node type.
   *
   * @param t node type
   * @return node kind
   */
  public static int kind(final NodeType t) {
    switch (t) {
      case DOC:
        return Data.DOC;
      case ELM:
        return Data.ELEM;
      case TXT:
        return Data.TEXT;
      case ATT:
        return Data.ATTR;
      case COM:
        return Data.COMM;
      case PI:
        return Data.PI;
      default:
        return -1;
    }
  }

  /**
   * Returns a node type for the specified database kind.
   *
   * @param k database kind
   * @return node type
   */
  public static NodeType type(final int k) {
    return TYPES[k];
  }

  @Override
  public final BXNode toJava() {
    return BXNode.get(deepCopy(new MainOptions()));
  }

  /**
   * Returns this Node's node type.
   *
   * @return node type
   */
  public final NodeType nodeType() {
    return (NodeType) type;
  }
}
Esempio n. 15
0
 @Override
 public long createCustomer(Customer customer) {
   customer.setId(id.incrementAndGet());
   customers.put(customer.getId(), customer);
   return customer.getId();
 }