请教一个关于内存资料移动的问题

yz1025 2012-08-29 11:30:54
程序中我定义了一个指针代表一个字符数组,里面储存大量的二进位字节,
我想透过代码去把一些资料过滤出来放到另一个字符数组里,累积到一定大
小就输出到档案中,想问C语言里有类似这种指令可用吗,类似sprintf的功
能,但是要存二进位字节资料。(不要C++或MFC或.NET)

目前是自己写函式去一段一段复制过去,但是速度好慢,之前直接用fwrite
速度更慢,猜想应该是IO存取次数过多的缘故。

简单说就是读取档案到内存,在进行过滤出一段段字节串,放到新内存位址
后,取得新资料,将资料批次输出到某一档案里。

P.S 来源资料档案约100MB〜1GB之间。
...全文
129 9 打赏 收藏 转发到动态 举报
写回复
用AI写文章
9 条回复
切换为时间正序
请发表友善的回复…
发表回复
yz1025 2012-09-07
  • 打赏
  • 举报
回复
最终追究问题点原因〜
其实是因为进度调的计算次数太多〜
导致速度变慢~~把代码改成每1万个字节算一次进度值〜
时间就省下来了〜当然直接把进度条拿掉速度最快〜
这就是根本的原因所在〜
Gloveing 2012-08-30
  • 打赏
  • 举报
回复
可以考虑使用内存映射
yz1025 2012-08-30
  • 打赏
  • 举报
回复
因为相同程式另一个功能将同一档案从字节转成字串并格式化也只需10~20秒,
同样是用内存资料搬移的方式。
jj+=sprintf(All[count]+jj, "AAA: %d|%d|%d", S_A,S_B,S_C);
-------------------------------------------------------------
所以6分钟实在太慢。
yz1025 2012-08-30
  • 打赏
  • 举报
回复
我用这几行直接把整个原始档以字节模式一次全读取进内存了,
想问的问题是内存之间的资料搬移要怎作效率比较高一点。
实际上已经能运行但是太慢要花上6分钟处理102459227个字节


unsigned long N_BUFFER_SIZE =GetFileLength2(stParam.SourceFile);
unsigned char *btaryBuffer=new unsigned char[N_BUFFER_SIZE];
FileSize=(long)N_BUFFER_SIZE;
while (nDataSize =fread(btaryBuffer,sizeof (char),N_BUFFER_SIZE, stream1))
{
for (nCount=0 ; nCount<nDataSize; nCount++)
{
if()
{
....
WriteDataToArray(btaryBuffer,nCount-2,sLen+2+1);
}
}
}

void WriteDataToArray(unsigned char *Str,long StartCount,__int16 EndCount)
{
long i,j;
for(i=StartCount;i<=StartCount+(long)EndCount;i++)
{
All[AllCount]=Str[i];
AllCount++;
}
if ((MAX_STSIZE-AllCount<100) || ((FileSize-StartCount-(long)EndCount)<5))
{
j =fwrite(All,sizeof (char), AllCount-1, stream2);
memset(All,0,sizeof(All));AllCount=0;
}
}


All Array 我大概开10〜100MB之间,还在测试多少时效率比较平均
实际上要怎改比较好一点?或是给点关键字?
ies_sweet 2012-08-30
  • 打赏
  • 举报
回复
I/O的性能的确不高
建议减少I/O操作次数
牺牲一些内存开销
yz1025 2012-08-30
  • 打赏
  • 举报
回复
我把

void WriteDataToArray(unsigned char *Str,long StartCount,__int16 EndCount)
{
long i,j;
for(i=StartCount;i<=StartCount+(long)EndCount;i++)
{
All[AllCount]=Str[i];
AllCount++;
}
if ((MAX_STSIZE-AllCount<100) || ((FileSize-StartCount-(long)EndCount)<5))
{
j =fwrite(All,sizeof (char), AllCount-1, stream2);
memset(All,0,sizeof(All));AllCount=0;
}
}

改成

void WriteDataToArray(unsigned char *Str,long StartCount,__int16 EndCount)
{
long j;
memcpy(All+AllCount,Str+StartCount,EndCount+1);
AllCount=AllCount+EndCount+1;

if ((MAX_STSIZE-AllCount<200) || ((FileSize-StartCount-(long)EndCount)<5))
{
j =fwrite(All,sizeof (char), AllCount-1, stream2);
memset(All,0,sizeof(All));AllCount=0;
}
}

后...

又有很奇怪的问题出现了,底层虽然是用C但是壳是用MFC,
MFC虽然比较容易一点,但是很肥又很慢(跟C比)。

只要把UI缩小10秒就完了,开着UI就要花上好几分钟,
但是同一支程式其他功能不会这样。
赵4老师 2012-08-30
  • 打赏
  • 举报
回复
仅供参考
#include <stdio.h>
#include <string.h>
char s[256];
char *p;
int r,n,i;
int main() {
while (1) {
printf("请输入一行文字(空行结束),\"%%20\"将替换为\" \",\"你懂得\"将替换为\"XXXXXX\":\n");
fgets(s,256,stdin);
if ('\n'==s[0]) break;
p=s;
while (1) {
p=strstr(p,"%20");
if (p) {
memmove(p+1,p+3,strlen(p)-3+1);
p[0]=' ';
} else break;
}
p=s;
while (1) {
p=strstr(p,"你懂得");
if (p) {
memmove(p+6,p+6,strlen(p)-6+1);
for (i=0;i<6;i++) p[i]='X';
} else break;
}
printf("%s",s);
}
return 0;
}
//请输入一行文字(空行结束),"%20"将替换为" ","你懂得"将替换为"XXXXXX":
//abcdefg%20helloworld%20something.pdf
//abcdefg helloworld something.pdf
//请输入一行文字(空行结束),"%20"将替换为" ","你懂得"将替换为"XXXXXX":
//这是测试文字你懂得,在这个你懂的地方,就得做你懂得的事
//这是测试文字XXXXX,在这个你懂的地方,就得做XXXXX的事
//请输入一行文字(空行结束),"%20"将替换为" ","你懂得"将替换为"XXXXXX":
//


图灵狗 2012-08-29
  • 打赏
  • 举报
回复
文档存取的速度远远慢于内存数据的移动,所以你应该尽可能的减少档案读写的次数,用fread/fwrite一批批的操作,字符串处理的函数有很多,比如strcpy/strcat/sprintf/sscanf等等。
寻找自我 2012-08-29
  • 打赏
  • 举报
回复
mmap?

69,371

社区成员

发帖
与我相关
我的任务
社区描述
C语言相关问题讨论
社区管理员
  • C语言
  • 花神庙码农
  • 架构师李肯
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告
暂无公告

试试用AI创作助手写篇文章吧