要疯掉了!

yingkundu 2009-07-15 03:22:14
程序目的:
很简单,读取当前的"read.txt"中的内容,把第一行与最末一行整体交换内容。然后另存到另一文件"write.txt"中。
比如:在read.txt中有:
aaa
bbbb
ccccc
dddddd
eeeeeee

交换之后就应该:
eeeeeee
dddddd
ccccc
bbbb
aaa
然后保存到write.txt

我的代码是:

#include<stdio.h>
2 #include<stdlib.h>
3 #include<string.h>
4
5 #define MAXNUM 20 //假设最多可处理20行,每行20个字符的数据段落
6 void putErrMessage(char *);
7 void putErrMessage(char *EMessage)
8 {
9 printf("Error happened,which is %s\n",EMessage);
10 exit(2);
11 }
12
13 int main()
14 {
15 FILE *fp_R;
16 FILE *fp_W;
17 char (*Buffer)[20];
18 Buffer=(char (*)[20])malloc(sizeof(char *)*20);
19 char temp[11];
20 memset(temp,'0',10);
21 int row=0,i=0,j=0;
22 int length=0;
23 if((fp_R=fopen("read.txt","r"))==NULL)
24 {
25 putErrMessage("Read Error");
26 }
27 if((fp_W=fopen("write.txt","w"))==NULL)
28 {
29 putErrMessage("Write Error");
30 }
31 while(fgets(temp,MAXNUM,fp_R)!=NULL)
32 {
33 strcpy(*(Buffer+row),temp);
34 row++;
35 }
36 for(i=row-1;i>=0;i--)
38 {
39 fprintf(fp_W,"%s",*(Buffer+i));
40 printf("%s",*(Buffer+i));
41 }
42
43 printf("OK2\n");
44
45 if(Buffer!=NULL)
46 {
47 for(i=0;i<20;i++)
48 free(*(Buffer+i));
49 free(Buffer);
50 }
51 printf("OK3\n");
52
53 if(fclose(fp_R)||fclose(fp_W))
54 {
55 putErrMessage("Close Error");
56 }
57 return 0;
58
59 }
但是,输出却是:

eeeeeee
$��dddddd
ccccc
bbbb
aaa
OK2
*** glibc detected *** ./test: free(): invalid next size (normal): 0x0960f008 ***
======= Backtrace: =========
/lib/tls/i686/cmov/libc.so.6[0xb7efd454]
/lib/tls/i686/cmov/libc.so.6(cfree+0x96)[0xb7eff4b6]
./test[0x8048888]
/lib/tls/i686/cmov/libc.so.6(__libc_start_main+0xe5)[0xb7ea4685]
./test[0x80485e1]
======= Memory map: ========
08048000-08049000 r-xp 00000000 08:07 123111 /home/duyingkun/test
08049000-0804a000 r--p 00000000 08:07 123111 /home/duyingkun/test
0804a000-0804b000 rw-p 00001000 08:07 123111 /home/duyingkun/test
0960f000-09630000 rw-p 0960f000 00:00 0 [heap]
b7d00000-b7d21000 rw-p b7d00000 00:00 0
b7d21000-b7e00000 ---p b7d21000 00:00 0
b7e70000-b7e7d000 r-xp 00000000 08:07 180531 /lib/libgcc_s.so.1
b7e7d000-b7e7e000 r--p 0000c000 08:07 180531 /lib/libgcc_s.so.1
b7e7e000-b7e7f000 rw-p 0000d000 08:07 180531 /lib/libgcc_s.so.1
b7e8d000-b7e8e000 rw-p b7e8d000 00:00 0
b7e8e000-b7fe6000 r-xp 00000000 08:07 197601 /lib/tls/i686/cmov/libc-2.8.90.so
b7fe6000-b7fe8000 r--p 00158000 08:07 197601 /lib/tls/i686/cmov/libc-2.8.90.so
b7fe8000-b7fe9000 rw-p 0015a000 08:07 197601 /lib/tls/i686/cmov/libc-2.8.90.so
b7fe9000-b7fed000 rw-p b7fe9000 00:00 0
b7ff8000-b7ffc000 rw-p b7ff8000 00:00 0
b7ffc000-b8016000 r-xp 00000000 08:07 180236 /lib/ld-2.8.90.so
b8016000-b8017000 r-xp b8016000 00:00 0 [vdso]
b8017000-b8018000 r--p 0001a000 08:07 180236 /lib/ld-2.8.90.so
b8018000-b8019000 rw-p 0001b000 08:07 180236 /lib/ld-2.8.90.so
bfe03000-bfe18000 rw-p bffeb000 00:00 0 [stack]
Aborted

我的问题是:

(1)“dddddd”前面的乱码是怎么出来的?怎样改过来?

(2)第19行我用的是数组来作临时数据用的,可否用指针来完成相似的功能?(请看题目中的功能)

(3) 后面的内存泄露的错误好像是由于free二维指针时发生的。这个错误如何改正?如何释放二维指针中的数据?

请 逐一进行讲解,不要含含糊糊!谢谢!


...全文
189 28 打赏 收藏 转发到动态 举报
写回复
用AI写文章
28 条回复
切换为时间正序
请发表友善的回复…
发表回复
yingkundu 2009-07-28
  • 打赏
  • 举报
回复
很遗憾,没有我想看到的结果
liberright 2009-07-22
  • 打赏
  • 举报
回复
用char** charstring去读取串,然后倒置不可以吗?
yylklshmyt20090217 2009-07-22
  • 打赏
  • 举报
回复
#include <stdio.h>
#include <string.h>

int main(void)
{
char string[100][100];
FILE *fp1,*fp2;
char buffer[100];
int i=0,j=0,k=0;
fp1= fopen("test1.txt","r");

while(fgets(buffer,100,fp1)!=NULL)
{
memcpy(string[i],buffer,100);
printf("%s\n",string[i]);
i++;
}

fclose(fp1);

printf("\n\n");

fp2=fopen("test2.txt","w+");


for(j=i-1;j>=0;j--)
{
printf("%s\n",string[j]);
fputs(string[j],fp2);

}
fclose(fp2);
}

比如:在read.txt中有:
aaa
bbbb
ccccc
dddddd
eeeeeee

交换之后就应该:
eeeeeee
dddddd
ccccc
bbbb
aaa
然后保存到write.txt


运行结果如预期所示。
happypeter2008 2009-07-18
  • 打赏
  • 举报
回复
我在努力调
yingkundu 2009-07-18
  • 打赏
  • 举报
回复
[Quote=引用 22 楼 thomascj 的回复:]
PS:我也要疯掉了。。。
[/Quote]
偶愚见:学好编程的关键在于勤动手,而不是观望性地“分析”一下。事实往往比你想象的更复杂。这也就是我只要代码不要评论的原因!
努力改程序,只要能调通,20分全给你!
thomasCJ 2009-07-17
  • 打赏
  • 举报
回复
哪位可以帮我这个问题看一下
Nio96 2009-07-16
  • 打赏
  • 举报
回复
char (*Buffer)[20];
Buffer=(char (*)[20])malloc(sizeof(char *)*20);

是因为你这个Buffer区没有清0?
Nio96 2009-07-16
  • 打赏
  • 举报
回复
原因是啥?指针换成了数组?字符串处理不好么?
yingkundu 2009-07-16
  • 打赏
  • 举报
回复
写错了,
12楼多了一行代码:length=strlen(temp);
去掉此行。
yingkundu 2009-07-16
  • 打赏
  • 举报
回复
已经被我搞定了,
代码如下:

#include<stdio.h>
#include<stdlib.h>
#include<string.h>

#define MAXNUM 20
void putErrMessage(char *);
void putErrMessage(char *EMessage)
{
printf("Error happened,which is %s\n",EMessage);
exit(2);
}

int main()
{
FILE *fp_R;
FILE *fp_W;
char Buffer[20][20];
char temp[20];
memset(temp,'\0',20);
int row=0,i=0,j=0;
int length=0;
if((fp_R=fopen("read.txt","r"))==NULL)
{
putErrMessage("Read Error");
}
if((fp_W=fopen("write.txt","w"))==NULL)
{
putErrMessage("Write Error");
}
while(fgets(temp,MAXNUM,fp_R)!=NULL)
{
length=strlen(temp);
strcpy(Buffer[row],temp);
row++;
}

for(i=row-1;i>=0;i--)
{
fprintf(fp_W,"%s",Buffer[i]);
printf("%s",Buffer[i]);
}

if(fclose(fp_R)||fclose(fp_W))
{
putErrMessage("Close Error");
}
return 0;

}


运行结果:
eeeeeee
dddddd
ccccc
bbbb
aaa

还有比这更完美的方法没有?
thomasCJ 2009-07-16
  • 打赏
  • 举报
回复
PS:我也要疯掉了。。。
thomasCJ 2009-07-16
  • 打赏
  • 举报
回复
#include <stdio.h>
#include <stdlib.h>
#include <assert.h>
#include <string.h>

#if 0
#define DEBUGP printf
#else
#define DEBUGP(format,args...)
#endif

#define MAX_LINE_LENGTH 10
#define MAX_STACK_LENGTH 100
#define ELEMTYPE char*

struct stack
{
int top;
ELEMTYPE str[MAX_STACK_LENGTH];
};

#if 1
int stack_is_empty(struct stack s)
{
return(s.top == -1);
}
#endif

void push(ELEMTYPE p, struct stack *s)
{
if(s->top == (MAX_STACK_LENGTH - 1))
{
exit(1);
}
s->str[++(s->top)] = p;
return;
}

ELEMTYPE pop(struct stack *s)
{
printf("top:%d\n", s->top);
return(s->str[s->top--]);
}

char *read_line(FILE *fp, char *line_buf)
{
char *ret = NULL;
char *p = NULL;

DEBUGP("%s begin\n", __FUNCTION__);
ret = fgets(line_buf, MAX_LINE_LENGTH, fp);
if((p = strchr(line_buf, '\n')) != NULL){
*p = '\0';
}
DEBUGP("%s end\n", __FUNCTION__);
return ret;
}

int main()
{
FILE *fp_r;
char *read_ret = NULL;
char buffer[MAX_LINE_LENGTH] = "";
struct stack file_stack;
int i = 0;
file_stack.top = -1;

if((fp_r = fopen("read.txt", "r")) == NULL)
{
printf("open error\n");
}
#if 1
while(1)
{
read_ret = read_line(fp_r, buffer);
if(!read_ret)
break;
//printf("%s\n", buffer);
push(buffer, &file_stack);
printf("%d %s\n", file_stack.top, file_stack.str[file_stack.top]);
}
#endif
#if 0
push('a', &file_stack);
push('b', &file_stack);
push('c', &file_stack);
push('d', &file_stack);
#endif
while(!stack_is_empty(file_stack))
{
printf("%s\n", pop(&file_stack));
//printf("top:%d string:%s\n", file_stack.top, file_stack.str[file_stack.top]);
//file_stack.top--;
}

return 0;
}

我的结果是
0 a
1 bb
2 ccc
3 ddddd
4 eeeeee
top:4
eeeeee
top:3
eeeeee
top:2
eeeeee
top:1
eeeeee
top:0
eeeeee
为什么push进去的时候对的,pop出来就只是最后一行了。。。我试过了字符的话可以,就是字符串不行
wren917403 2009-07-16
  • 打赏
  • 举报
回复
这是纯的c语言?
flameearth 2009-07-16
  • 打赏
  • 举报
回复
1 std::list<string::string> lstString;
2 使用geline()循环读取每行的内容
3 listString.push_back(str);
4 listString.sort(); 倒序后 在写入文件
zbihong 2009-07-16
  • 打赏
  • 举报
回复
牛!
yingkundu 2009-07-16
  • 打赏
  • 举报
回复
有人出来替我总结一下原因的吗??
yingkundu 2009-07-16
  • 打赏
  • 举报
回复
12楼的算法虽然能满足要求,但缺点是:必须得把文章段落中所有的字符复制到数组中,如果段落比较小,还可以。但是,如果段落很长,再去定义一个大数组就不方便了。所以,基于此缺点,我又改了算法:首先把文件指针移动到read.txt的最后一行的开始处,然后在复制最后一行到temp数组中,然后再从temp中复制到write.txt中。然后,再往上移动文件指针到倒数第二行,再复制,…………如此反复,一直到文件开头行。代码如下:

int main()
{
FILE *fp_R;
FILE *fp_W;
char temp[MAXNUM];
char line_length[20];
char ch=0;
memset(temp,'\0',MAXNUM-1);
int i=0,j=0;
int index=0;
int line_len=0;
if((fp_R=fopen("read.txt","r"))==NULL)
{
putErrMessage("Read Error");
}
if((fp_W=fopen("write.txt","w"))==NULL)
{
putErrMessage("Write Error");
}
while((ch=getc(fp_R))!=EOF)//To store every line's charactor number in an array
{
if(ch!='\n')
{
line_len++;
}
else
{
line_length[index]=line_len;
line_len=0;
index++;
}

}
fseek(fp_R,-(line_length[index-1]+1),SEEK_END);
for(i=index-1;i>=0;i--)
{
fgets(temp,line_length[i]+1,fp_R);
strcat(temp,"\n\0");
printf("%s",temp);
fprintf(fp_W,"%s",temp);
fseek(fp_R,-(line_length[i]+line_length[i-1]+1),SEEK_CUR);
index--;
}

return 0;
}

注:已经省略了头文件和putErrMessage()。

运行结果:
gggggggg
fffffff
eeeeee
ddddd
cccc
bbb
aa

运行得很好,而且无论文章有多长都可以!

selooloo 2009-07-15
  • 打赏
  • 举报
回复
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#define LEN 20

int main(void)
{
FILE *fp1,*fp2;
char temp[LEN][LEN],t[LEN];
char ch;
int i=0,j=0,k;

if((fp1=fopen("read.txt","r"))==NULL)
{
puts("Can't open file");
exit(1);
}

while((ch=getc(fp1))!=EOF)
{
if(ch!='\n')
{
temp[j][i]=ch;
i++;
}
else
{
temp[j][i]='\0';
j++;
i=0;
}
}

strcpy(t,temp[0]);
strcpy(temp[0],temp[j-1]);
strcpy(temp[j-1],t);

if((fp2=fopen("write.txt","w"))==NULL)
{
printf("Can't creat file\n");
exit(1);
}
for(k=0;k<j;k++)
fprintf(fp2,"%s\n",temp[k]);
fclose(fp1);
fclose(fp2);

system("pause");
return 0;
}
yingkundu 2009-07-15
  • 打赏
  • 举报
回复
出现新问题了:
当我把read.txt里面的文字增加了两行后,即:
aa
bbb
cccc
ddddd
eeeeee
fffffff
ggggggg

输出:
eeeeee
ddddd
cccc
bbb
aa

为什么f和g所在的行没有了呢?

有没有人把我的代码在自己电脑上敲一下试试呢?没有的话就别说些不着边际的话。
期待高手~~~~
okeyes 2009-07-15
  • 打赏
  • 举报
回复
那是文件头吧。你应该把最开始读到的数据"FF"或"FE"去掉。
加载更多回复(8)

69,373

社区成员

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

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