如何将 2048 位的 BigInteger 拆分成固定数量的 64 位的字?
How to split the 2048 bits BigInteger into words with a fixed number of 64 bits?
我有一个包含 2048 位 BigInteger 数字的密钥。我想把它分解成固定数量的 64 位的单词,然后计算所有这些单词的异或; java 谁能帮我实现这个?
示例:
Big Number(key):
11380312415897726212538720767584623938377542218843650885786488543557849920563944820657401556147072220807050423844611527817088743264179887246035449031879964033048917437051768727745163996083995699396309860629605332639267450328379289961205789359923142431676348109877819086396004913235006262427231898532203764657706261780748597526471127787542155628754978941021278802504747939847153450812209928520258539639347968927907337576400038705453704498741239631581573919339705649004208586949422810873621196157474272177586468236634536851618181572350294408509526514361027546939234421045026063811415872877733865949984217287267027217419
output(parity checksum:) 10249015871569703692
这是我实现的方法,但它不能正常工作:
/**
* *
* Receives a 2048 bits key and applies a word by word XOR to yield a 64 bit
* integer at the end.
*
* @param key 2048 bit integer form part A1 DH Key Exchange Protocol
* @return A 64 bit integer
*/
public static BigInteger parityWordChecksum(BigInteger key) {
LongBuffer buffer = ByteBuffer.wrap(key.toByteArray()).asLongBuffer();
long xor = 0;
while (buffer.hasRemaining()) {
xor ^= buffer.get();
}
return BigInteger.valueOf(xor);
}
您的代码大部分是正确的,但是,Java long
是 已签名的 ,但您的预期输出假定它是未签名的。您可以通过将 BigInteger.valueOf
替换为适当的 BigInteger
构造函数(并进行一些按摩以从 long
值获取 byte
数组来轻松解决此问题,如下所示:
public static BigInteger parityWordChecksum(BigInteger key) {
LongBuffer buffer = ByteBuffer.wrap(key.toByteArray()).asLongBuffer();
long xor = 0;
while (buffer.hasRemaining()) {
xor ^= buffer.get();
}
ByteBuffer result = ByteBuffer.allocate(8);
result.putLong(xor);
return new BigInteger(1, result.array()); // Signum 1 for unsigned
}
输出:
10249015871569703692
如果你只想在你的方法中使用 BigInteger
s(而不是 long),你可以这样做:
public static BigInteger parityWordChecksum(final BigInteger key) {
BigInteger result = new BigInteger("0");
BigInteger mask = BigInteger.ZERO;
for (int i = 0; i < 64; i++) {
mask = mask.setBit(i);
}
for (int i = 0; i < 2048; i += 64) {
result = result.xor(key.shiftRight(i).and(mask));
}
return result;
}
我有一个包含 2048 位 BigInteger 数字的密钥。我想把它分解成固定数量的 64 位的单词,然后计算所有这些单词的异或; java 谁能帮我实现这个?
示例:
Big Number(key): 11380312415897726212538720767584623938377542218843650885786488543557849920563944820657401556147072220807050423844611527817088743264179887246035449031879964033048917437051768727745163996083995699396309860629605332639267450328379289961205789359923142431676348109877819086396004913235006262427231898532203764657706261780748597526471127787542155628754978941021278802504747939847153450812209928520258539639347968927907337576400038705453704498741239631581573919339705649004208586949422810873621196157474272177586468236634536851618181572350294408509526514361027546939234421045026063811415872877733865949984217287267027217419
output(parity checksum:) 10249015871569703692
这是我实现的方法,但它不能正常工作:
/**
* *
* Receives a 2048 bits key and applies a word by word XOR to yield a 64 bit
* integer at the end.
*
* @param key 2048 bit integer form part A1 DH Key Exchange Protocol
* @return A 64 bit integer
*/
public static BigInteger parityWordChecksum(BigInteger key) {
LongBuffer buffer = ByteBuffer.wrap(key.toByteArray()).asLongBuffer();
long xor = 0;
while (buffer.hasRemaining()) {
xor ^= buffer.get();
}
return BigInteger.valueOf(xor);
}
您的代码大部分是正确的,但是,Java long
是 已签名的 ,但您的预期输出假定它是未签名的。您可以通过将 BigInteger.valueOf
替换为适当的 BigInteger
构造函数(并进行一些按摩以从 long
值获取 byte
数组来轻松解决此问题,如下所示:
public static BigInteger parityWordChecksum(BigInteger key) {
LongBuffer buffer = ByteBuffer.wrap(key.toByteArray()).asLongBuffer();
long xor = 0;
while (buffer.hasRemaining()) {
xor ^= buffer.get();
}
ByteBuffer result = ByteBuffer.allocate(8);
result.putLong(xor);
return new BigInteger(1, result.array()); // Signum 1 for unsigned
}
输出:
10249015871569703692
如果你只想在你的方法中使用 BigInteger
s(而不是 long),你可以这样做:
public static BigInteger parityWordChecksum(final BigInteger key) {
BigInteger result = new BigInteger("0");
BigInteger mask = BigInteger.ZERO;
for (int i = 0; i < 64; i++) {
mask = mask.setBit(i);
}
for (int i = 0; i < 2048; i += 64) {
result = result.xor(key.shiftRight(i).and(mask));
}
return result;
}