【问题标题】:How to efficiently store a large Java map?如何高效地存储大型 Java 地图?
【发布时间】:2017-04-09 06:00:02
【问题描述】:

我正在暴力破解一场比赛,我需要存储所有位置和结果的数据。数据可能有数百 Gb 的大小。我考虑过 SQL,但我担心紧密循环中的查找可能会降低性能。程序将迭代可能的位置,如果已知,则返回获胜的移动,如果已知所有移动都失败,则返回最长的失败序列,并检查未知移动的结果。

存储大的Map<Long,Long[]> positionIdToBestMoves 的最佳方式是什么?我正在考虑 SQL 或数据序列化。

我想通过暴力破解 Java 中所有可行的移动来解决微小的跳棋。持仓上限在1000亿左右。它们中的大多数是不合理的(即比游戏开始时出现的更多)。大约 100 亿是一个合理的估计。每个Map<Long, Long[]> positionLong positionID 映射到Long whiteToMoveLong blackToMove。正值表示头寸获胜,应选择导致头寸存储在价值中的移动。负值-n 表示位置最多在n 移动。

搜索本身会有这样的递归:

//this is a stub

private Map<Long, Long[]> boardBook =...

//assuming that all winning positions are known
public Long nextMove(Long currentPos, int whiteOrBlack){
Set<Long> validMoves = calculateValidMoves(currentPos, whiteOrBlack);
boolean hasWinner = checkIfValidMoveIsKnownToWin(validMoves, whiteOrBlack);

if(hasWinner){  //there is a winning move - play it
    Long winningMove = getWinningMove(validMoves, whiteOrBlack);
    boardBook.get(currentPos)[whiteOrBlack] = winningMove ;    
    return winningMove ;
    }
boolean areAllPositionsKnown = checkIfAllPositionsKnown(validMoves, whiteOrBlack);
if(areAllPositionsKnown){  //all moves are losing.. choose longest struggle
    Long longestSequenceToDefeat = findPositionToLongestSequenceToDefeat(validMoves, whiteOrBlack);
    int numberOfStepsTodefeat = boardBook.get(longestSequenceToDefeat)[whiteOrBlack];
    boardBook.get(currentPos)[whiteOrBlack] = longestSequenceToDefeat ;
    return longestSequenceToDefeat;
    }

Set<Long> movesToCheck = getUntestedMoves(validMoves, whiteOrBlack);
Long longeststruggle;
int maxNumberOfMovesToDefeat =-1;
for(Long moveTocheck : movesToCheck){
    Long result = nextMove(moveToCheck, whiteOrBlack);
    if(result>0){ //just discovered a winning move
            boardBook.get(currentPos)[whiteOrBlack] = winningMove ;    
            return winningMove ;
        }else {
            int numOfMovesToDefeat = -1*boardBook.get(moveTocheck)[whiteOrBlack];
            if( numOfMovesToDefeat >maxNumberOfMovesToDefeat ){
                 maxNumberOfMovesToDefeat =numOfMovesToDefeat ; 
                 longeststruggle = moveTocheck;
                  }
         }
      }
boardBook.get(currentPos)[whiteOrBlack] = -1*maxNumberOfMovesToDefeat;
return  longeststruggle;
}

【问题讨论】:

  • 有趣的问题。这超出了我的回答能力,但你所描述的听起来更像是大数据/NoSQL 解决方案的领域,而不是传统的 SQL。

标签: java sql large-data


【解决方案1】:

您可能想查看Chronicle。它是高度优化的键值存储,应该适合您的用途。

或者您可以自己编写存储,但您最终还是会在后台执行诸如映射和内存映射文件之类的操作。

【讨论】:

    猜你喜欢
    • 2012-07-02
    • 2019-07-07
    • 2018-01-31
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2012-10-31
    • 2015-03-28
    相关资源
    最近更新 更多