在静脉中获取所有相似的块

我正在尝试将所有类似的块放在一起。但是我的代码似乎只在 5 x 5 块半径内获取块。


我尝试使用一种方法


public List<Block> getVein(Block b){

    List<Block> blocks = similarNear(null, b);

    ListIterator<Block> toCheck = blocks.listIterator();

    while(toCheck.hasNext()) {

        Block current = toCheck.next();

        if(!blocks.contains(current))

            blocks.add(current);

        for(Block block : similarNear(blocks, current)) {

            if(!blocks.contains(block))

                toCheck.add(block);

        }

    }

    return blocks;

}

我还想添加一个上限说示例只允许它打破 25 个块,但我不知道如何添加它而不阻止它在一个方向上找到 25 个块然后停止(如果有任何意义)。


慕村9548890
浏览 127回答 1
1回答

MM们

在这里,我尝试尽可能地注释代码,任何建议表示赞赏。//Loops around a block to find other blocks that matches with the center (the given block)private ArrayList<Block> search(Block center) {&nbsp; &nbsp; //The maximum amount of blocks to find (the 'cap', our limit)&nbsp; &nbsp; final int max = 25;&nbsp; &nbsp; ArrayList<Block> blocks = new ArrayList<>();&nbsp; &nbsp; Queue<Block> toSearch = new LinkedList<>();&nbsp; &nbsp; //Add the center to list, so it has something to start the search&nbsp; &nbsp; toSearch.add(center);&nbsp; &nbsp; //While we have something to search and have not reached the limit (the 'cap')&nbsp; &nbsp; while (toSearch.size() > 0 && blocks.size() < max) {&nbsp; &nbsp; &nbsp; &nbsp; Block b = toSearch.remove(); //Get the block on top of the queue, (and remove it)&nbsp; &nbsp; &nbsp; &nbsp; blocks.add(b); //Since this block is already of the type we want, we add it the found list (in this case is the 'blocks' var)&nbsp; &nbsp; &nbsp; &nbsp; //Find all its neighbours&nbsp; &nbsp; &nbsp; &nbsp; for (Block around : findNeighbours(b)) {&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; //We do this check here too 'cause findNeighbours() might return up to 26 blocks and it might be too much&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; //eg. we have a max of 50 blocks and have already found 45, if findNeighbours find more than five blocks we want to ignore to others&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; //that way we stay within our limit, and once this check is made once the whole loop will end&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; if (blocks.size() >= max) {&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; break;&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; }&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; //Only add this block if not yet found/processed/searched&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; if (toSearch.contains(around) || blocks.contains(around)) {&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; continue;&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; }&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; toSearch.add(around);&nbsp; &nbsp; &nbsp; &nbsp; }&nbsp; &nbsp; &nbsp; &nbsp; //If in our toSearch list we already enough blocks to fill our limit we stop the search and add as much as we need to fill up out limit.&nbsp; &nbsp; &nbsp; &nbsp; //This can save some resources when searching for common blocks like dirt and stone, which we might find a lot and not all of them will be added to our list&nbsp; &nbsp; &nbsp; &nbsp; if (toSearch.size() + blocks.size() >= max) {&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; int remains = max - blocks.size(); //Gets how many more blocks we need to fulfill our goal (the limit)&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; for (int i = 0; i < remains; i++) {&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; blocks.add(toSearch.remove());&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; }&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; break;&nbsp; &nbsp; &nbsp; &nbsp; }&nbsp; &nbsp; }&nbsp; &nbsp; return blocks;}//Finds all neighbours around a blockprivate List<Block> findNeighbours(Block block) {&nbsp; &nbsp; //to avoid a bunch of ifs we use these 3 fors to loop over each axis (X, Y, Z)&nbsp; &nbsp; ArrayList<Block> blocks = new ArrayList<>();&nbsp; &nbsp; //SQUARED 'radius' to search around&nbsp; &nbsp; final int searchRadius = 1;&nbsp; &nbsp; for (int x = -searchRadius; x <= searchRadius; x++) {&nbsp; &nbsp; &nbsp; &nbsp; for (int y = -searchRadius; y <= searchRadius; y++) {&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; for (int z = -searchRadius; z <= searchRadius; z++) {&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; if (x == 0 && y == 0 && z == 0) {continue;}&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; //Get the block at this location (x,y,z)&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; Block near = block.getLocation().clone().add(x, y, z).getBlock();&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; //Check if the found block is a valid match. eg: is the same type, has the same data/variant&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; if (match(near, block)) {&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; blocks.add(near);&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; }&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; }&nbsp; &nbsp; &nbsp; &nbsp; }&nbsp; &nbsp; }&nbsp; &nbsp; return blocks;}//Checks if a matches to bprivate boolean match(Block a, Block b) {&nbsp; &nbsp; //Checks only the block type, ot its variant/data&nbsp; &nbsp; //return a.getType() == b.getType();&nbsp; &nbsp; //Checks its type and its data/variant (might not work on all bukkit/spigot versions)&nbsp; &nbsp; return a.getType() == b.getType() && a.getState().getData().equals(b.getState().getData());}
打开App,查看更多内容
随时随地看视频慕课网APP

相关分类

Java