我正在尝试测试WKdm算法,看看它对100KB,1MB和10MB的缓冲区的性能如何;但是,在我的测试程序中,任何大于1KB的缓冲区都会抛出EXC_BAD_ACCESS:无法访问内存。
我使用了WKdm.c的main(),这是一个简单的测试,并尝试转换它,以便我可以更改要压缩的输入缓冲区的大小。
我正在使用WKDM算法的标准Scott Kaplan实现,该算法由源文件和头文件组成,找到here。我试过Linux和OS X 32位。
#include <stdio.h>
#include <unistd.h>
#include <math.h>
#include <strings.h>
#include <sys/time.h>
#include "WKdm.h"
#define PAGE_SIZE_IN_WORDS 1024
#define PAGE_SIZE_IN_BYTES 4096
int main() {
WK_word i;
//int testSize = 1024; //1KB Works
int testSize = 102400; //100KB causes EXC_BAD_ACCESS
int testNumWords = testSize / sizeof(WK_word);
printf("testSize = %d bytes or %d words\n", testSize, testNumWords);
WK_word* source_buf = (WK_word*) malloc(testSize * 2);
WK_word* dest_buf = (WK_word*) malloc(testSize * 2);
WK_word* udest_buf = (WK_word*) malloc(testSize * 2);
for (i = 0; i < testNumWords; i++) {
source_buf[i] = rand() % 1000; //Semi-random: 0-999 stored in each 4-byte word
}
source_buf[testNumWords + 1] = 99999;
udest_buf[testNumWords + 1] = 55555;
printf("first 50 words of source_buf are:\n");
for (i = 0; i < 50; i++)
printf(" %d", source_buf[i]);
fflush(stdout);
struct timeval t0; struct timeval t1;
gettimeofday(&t0, 0);
// Compress the source_buf into the dest_buf
i = WKdm_compress(source_buf, dest_buf, testNumWords);
gettimeofday(&t1, 0);
long elapsed = (t1.tv_sec - t0.tv_sec) * 1000000 + t1.tv_usec - t0.tv_usec;
printf("\nWKdm_compress size in bytes: %u\n", i);
printf("Time to compress: %lu microseconds\n\n", elapsed);
printf("redzone value at end of source buf (should be 99999) is %u\n",
source_buf[testNumWords + 1]); fflush(stdout);
gettimeofday(&t0, 0);
WKdm_decompress(dest_buf, udest_buf, testNumWords);
gettimeofday(&t1, 0);
elapsed = (t1.tv_sec - t0.tv_sec) * 1000000 + t1.tv_usec - t0.tv_usec;
printf("Time to decompress: %lu microseconds\n\n", elapsed);
printf("redzone value at end of udest buf (should be 55555) is %u\n", udest_buf[testSize + 1]);
printf("first 50 words of udest_buf are:\n");
for (i = 0; i < 50; i++)
printf(" %d", udest_buf[i]);
i = bcmp(source_buf, udest_buf, 100);
printf("\nbcmp of orig. and compr'd/decompr'd copy (should be 0) is %u\n", i);
fflush(stdout);
return 0;
}
答案 0 :(得分:2)
Scott Kaplan实现的WKdm算法是针对4KB的页面大小而设计的。如果要压缩大于4KB的任何内容,则需要在建模期间增加用于以中间形式保存输出数据的数组的大小。这三个数组位于WKdm_compress和WKdm_decompress函数的顶部。您可以增加它们的大小来存储更多的中间数据,但是看起来comp / decomp时间会急剧增加。
此外,压缩大于1MB的缓冲区会导致更多超出范围的异常。因此,除非您想要进行大量的重写,否则您可能只想将WKdm用于小于4KB的缓冲区。
作为旁注,Kaplan的WKdm实现针对压缩4KB进行了优化这一事实可能是Apple在OS X 10.9 Mavericks中使用它进行内存压缩的一个重要原因,它的页面大小为4KB。