【发布时间】:2011-03-05 04:00:12
【问题描述】:
系统编程中的当前项目是想出一个 ASCII 压缩器,它会删除顶部的零位并将内容写入文件。
为了方便解压,先将原始文件大小写入file,然后是压缩后的char字节。有两个文件可以运行测试——一个是 63 字节长,另一个是 5344213 字节。我的代码在第一个测试文件中按预期工作,因为它写入了 56 字节的压缩文本和 4 字节的文件头。
但是,当我在长测试文件上尝试时,压缩版本比原始文件短 3 个字节,当时它应该大约小 749KiB,或原始大小的 14%。我已经计算出长测试文件的前两个写入循环的二进制位移值,它们与我的测试打印输出中记录的内容相匹配。
while ( (characters= read(openReadFile, unpacked, BUFFER)) >0 ){
unsigned char packed[7]; //compression storage
int i, j, k, writeCount, endLength, endLoop;
//loop through the buffer array
for (i=0; i< characters-1; i++){
j= i%7;
//fill up the compressed array
packed[j]= packer(unpacked[i], unpacked[i+1], j);
if (j == 6){
writeCalls++; //track how many calls made
writeCount= write(openWriteFile, packed, sizeof (packed));
int packedSize= writeCount;
for (k=0; k<7 && writeCalls < 10; k++)
printf("%X ", (int)packed[k]);
totalWrittenBytes+= packedSize;
printf(" %d\n", packedSize);
memset(&packed[0], 0, sizeof(packed)); //clear array
if (writeCount < 0)
printOpenErrors(writeCount);
}
//end of buffer array loop
endLength= characters-i;
if (endLength < 7){
for (endLoop=0; endLoop < endLength-1; endLoop++){
packed[endLoop]= packer(unpacked[endLoop], unpacked[endLoop+1], endLoop);
}
packed[endLength]= calcEndBits(endLength, unpacked[endLength]);
}
} //end buffer array loop
} //end file read loop
打包函数:
//calculates the compressed byte value for the array
char packer(char i, char j, int k){
char packStyle;
switch(k){
//shift bits based on mod value with 8
case 0:
packStyle= ((i & 0x7F) << 1) | ((j & 0x40) >> 6);
break;
case 1:
packStyle= ((i & 0x3F) << 2) | ((j & 0x60) >> 5);
break;
case 2:
packStyle= ((i & 0x1F) << 3) | ((j & 0x70) >> 4);
break;
case 3:
packStyle= ((i & 0x0F) << 4) | ((j & 0x78) >> 3);
break;
case 4:
packStyle= ((i & 0x07) << 5) | ((j & 0x7C) >> 2);
break;
case 5:
packStyle= ((i & 0x03) << 6) | ((j & 0x7E) >> 1);
break;
case 6:
packStyle= ( (i & 0x01 << 7) | (j & 0x7F));
break;
}
return packStyle;
}
我已验证每次刷新打包缓冲区时都会写入 7 个字节,并且对长文件进行了 763458 次写入调用,匹配最多写入 5344206 个字节。
我从打印输出中得到的十六进制代码与我事先以二进制形式计算的相同,我可以看到每个字节的最高位被删除。那么为什么位移没有反映在结果中呢?
【问题讨论】:
-
@Andrew 听起来像,但如果是这样,让 Jason 标记它,只是为了确定。无论如何,这是一个很好的问题
-
@Andrew & Earlz,这是作业,但是目前 SO 的态度是不应该使用作业标签,所以这就是我避免使用它的原因。另外,在第一段中,我说这是一个系统编程项目
-
啊,我在 Meta 的更新还不够多,无法了解社区当前的偏好:P
标签: c compression bit-manipulation