Không có cách nào để thực hiện trực tiếp. Các máy tính đơn vị nhỏ nhất có thể xử lý là một byte (thậm chí booleans mất một byte). Tuy nhiên bạn có thể tạo một lớp dòng tùy chỉnh gói một byte với các bit bạn muốn rồi viết nó. Sau đó, bạn có thể tạo ra một trình bao bọc cho lớp này, chức năng ghi của nó có một số kiểu không thể tách rời, kiểm tra rằng nó nằm trong khoảng từ 0 đến 7 (hoặc -4 và 3 ... hoặc bất kỳ thứ gì), trích xuất các bit theo cùng cách với lớp BitInputStream (bên dưới) và thực hiện các cuộc gọi tương ứng với phương thức ghi của BitOutputStream. Bạn có thể nghĩ rằng bạn chỉ có thể làm cho một bộ các lớp dòng IO, nhưng 3 không đi vào 8 đồng đều.Vì vậy, nếu bạn muốn hiệu quả lưu trữ tối ưu và bạn không muốn làm việc thực sự khó khăn, bạn đang loại mắc kẹt với hai lớp trừu tượng. Dưới đây là một lớp BitOutputStream, một lớp BitInputStream tương ứng và một chương trình đảm bảo chúng hoạt động.
import java.io.IOException;
import java.io.OutputStream;
class BitOutputStream {
private OutputStream out;
private boolean[] buffer = new boolean[8];
private int count = 0;
public BitOutputStream(OutputStream out) {
this.out = out;
}
public void write(boolean x) throws IOException {
this.count++;
this.buffer[8-this.count] = x;
if (this.count == 8){
int num = 0;
for (int index = 0; index < 8; index++){
num = 2*num + (this.buffer[index] ? 1 : 0);
}
this.out.write(num - 128);
this.count = 0;
}
}
public void close() throws IOException {
int num = 0;
for (int index = 0; index < 8; index++){
num = 2*num + (this.buffer[index] ? 1 : 0);
}
this.out.write(num - 128);
this.out.close();
}
}
Tôi chắc chắn có cách để đóng gói int với các nhà khai thác bit-khôn ngoan và do đó tránh phải đảo ngược đầu vào, nhưng tôi không nghĩ gì khó.
Ngoài ra, bạn có thể nhận thấy rằng không có cách nào địa phương để phát hiện rằng các bit cuối cùng đã được đọc trong việc thực hiện điều này, nhưng tôi thực sự không muốn nghĩ rằng cứng.
import java.io.IOException;
import java.io.InputStream;
class BitInputStream {
private InputStream in;
private int num = 0;
private int count = 8;
public BitInputStream(InputStream in) {
this.in = in;
}
public boolean read() throws IOException {
if (this.count == 8){
this.num = this.in.read() + 128;
this.count = 0;
}
boolean x = (num%2 == 1);
num /= 2;
this.count++;
return x;
}
public void close() throws IOException {
this.in.close();
}
}
Bạn có thể biết điều này, nhưng bạn nên đặt BufferedStream vào giữa BitStream và FileStream của bạn hoặc sẽ mất vĩnh viễn.
import java.io.BufferedInputStream;
import java.io.BufferedOutputStream;
import java.io.File;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.IOException;
import java.util.Random;
class Test {
private static final int n = 1000000;
public static void main(String[] args) throws IOException {
Random random = new Random();
//Generate array
long startTime = System.nanoTime();
boolean[] outputArray = new boolean[n];
for (int index = 0; index < n; index++){
outputArray[index] = random.nextBoolean();
}
System.out.println("Array generated in " + (double)(System.nanoTime() - startTime)/1000/1000/1000 + " seconds.");
//Write to file
startTime = System.nanoTime();
BitOutputStream fout = new BitOutputStream(new BufferedOutputStream(new FileOutputStream("booleans.bin")));
for (int index = 0; index < n; index++){
fout.write(outputArray[index]);
}
fout.close();
System.out.println("Array written to file in " + (double)(System.nanoTime() - startTime)/1000/1000/1000 + " seconds.");
//Read from file
startTime = System.nanoTime();
BitInputStream fin = new BitInputStream(new BufferedInputStream(new FileInputStream("booleans.bin")));
boolean[] inputArray = new boolean[n];
for (int index = 0; index < n; index++){
inputArray[index] = fin.read();
}
fin.close();
System.out.println("Array read from file in " + (double)(System.nanoTime() - startTime)/1000/1000/1000 + " seconds.");
//Delete file
new File("booleans.bin").delete();
//Check equality
boolean equal = true;
for (int index = 0; index < n; index++){
if (outputArray[index] != inputArray[index]){
equal = false;
break;
}
}
System.out.println("Input " + (equal ? "equals " : "doesn't equal ") + "output.");
}
}
Nguồn
2014-09-23 08:53:02
Dường như tôi sẽ phải đọc/ghi byte và tìm hiểu các hoạt động bit ... Cảm ơn mọi người vì câu trả lời ... –
Cảm ơn bạn, cho điểm hiệu quả ... –
Bởi anding b and 0x3, aren 't chỉ có 2 bit quan trọng nhất được bảo tồn trong lowbits? –