Java에서 이진 파일을 읽으려고합니다. 부호없는 8 비트 값, 부호없는 16 비트 값 및 부호없는 32 비트 값을 읽는 방법이 필요합니다. 이 작업을 수행하는 최선의 방법은 무엇입니까 (가장 빠르고 멋진 코드)? 나는 C++로 이런 짓을하고이 같은 짓습니다 :이 경우 예를 버퍼에 문제가 발생 4 바이트를 부호없는 32 비트 정수로 변환하고 long에 저장하십시오.
uint8_t *buffer;
uint32_t value = buffer[0] | buffer[1] << 8 | buffer[2] << 16 | buffer[3] << 24;
그러나 자바
를 [1]은이 비트 왼쪽의 결과로 설정 로그인 값을 포함 shift는 int (?)입니다. OR 대신 : 특정 장소에서 0xA5 만 보내면 OR : 0xFFFFA500 또는 그와 비슷한 것으로 두 개의 상위 바이트를 "손상"시킵니다.나는 지금과 같이 보이는 코드를 가지고 :
public long getUInt32() throws EOFException, IOException {
byte[] bytes = getBytes(4);
long value = bytes[0] | (bytes[1] << 8) | (bytes[2] << 16) | (bytes[3] << 24);
return value & 0x00000000FFFFFFFFL;
}
나는 4 바이트 결과 0 × 50 0x67 0xA5 0x72을 변환 할 경우
대신 0x5072A567의 0xFFFFA567입니다.편집 :
public long getUInt32() throws EOFException, IOException {
byte[] bytes = getBytes(4);
long value = bytes[0] & 0xFF;
value |= (bytes[1] << 8) & 0xFFFF;
value |= (bytes[2] << 16) & 0xFFFFFF;
value |= (bytes[3] << 24) & 0xFFFFFFFF;
return value;
}
을하지만이 할 수있는 더 좋은 방법이되지 않습니다 :이 위대한 작품? 10 비트 동작은 이와 같은 단순한 것보다 훨씬 "비트"가 많습니다. (내가 뭘했는지 보시라.) =)
사용하는 변수가 긴 경우 ALU는 항상 64 비트의 연산을 수행합니다. 변수가 int 인 경우 ALU는 항상 32 비트에서 연산을 수행하고 (ALU 기능의 나머지 32 비트는 사용하지 않습니다). 바이트에 대한 연산은 ALU의 58 비트를 사용하지 않을 가능성이 높습니다. 이러한 작업은 항상 1 클럭 사이클에서 이루어 지므로 좋은 10 비트라는 "비트"가 너무 많지는 않습니다. –
아니, 귀하의 작업 구현은 바로 올바른 접근 방식입니다. –
위의 코드에서 마지막 비트 및 연산이 필요하지 않습니다. value | = (bytes [3] << 24) & 0xFFFFFFFF; –