【发布时间】:2015-02-03 13:46:13
【问题描述】:
这是对K&R教科书的一个练习的一个非常奇怪的疑问,我不知道“标准”答案是什么,所以程序本身可能有点陌生。
我试图在代码中描述将这个程序组合在一起的增量步骤,我的问题是关于按逻辑不应该产生任何影响但带走流浪--i的调整。
相反,如果我尝试它,就会出现各种奇怪的行为(我尝试了一些组合,所以我不会在这里描述它们。)
#include <stdio.h>
#define MAXCHAR 15
int storeline(char line[], int lim);
void reverse(char in[], char out[], int len);
main() {
int l;
char line[MAXCHAR+2]; /*I add two position to accomodate a newline and a '\0' character */
char enil[MAXCHAR+2];
while ((l=storeline(line, MAXCHAR+2))>=0) {
if (l<MAXCHAR)
reverse(line, enil, l); /*reverse is called with the array (in this case a 17 characters array) and the count computed in storeline (up to )*/
else
reverse(line, enil, MAXCHAR);
printf("%s", enil);
}
return 0;
}
int storeline(char s[], int lim) {
int i;
int c;
for(i=0;i<lim-2&&(c=getchar())!='\n'&&c!=EOF;++i){ /* this loop breaks at i==15 */
if (c==' '||c=='\t') {
while((c=getchar())==' '||c=='\t');
s[i]=' ';
++i;
if(c==EOF)
break;
}
s[i]=c;
}
if (c!=EOF) {
s[i]='\n'; /* a newline is added in s[15] */
++i;
}
s[i]='\0'; /* a '\0' character is added at s[16] */
--i; /*no more characters have to be added so I bring the count of the characters down by 1 (a further unit is deducted by the fact that one character is stored in s[0] */
while (c!='\n' && c!= EOF) {
c=getchar();
i++;
}
return i; /* the count goes on and is subsequently returned by the function, newline is assumed to be a file break by design, but this is easily adjusted */
}
/* let's pretend the string was '123451234512345' and MAXCHAR is 15. */
void reverse (char in[], char out[], int len) {
int i, lim;
i=0;
lim=len-1; /*len was 15, now it is 14. note that the array goes up to in[16] */
while(lim>=0) {
out[i]=in[lim];
++i;
--lim;
}
out[i]='\n';
++i;
out[i]='\0';
}
我的疑问是,如果我删除 storeline 中的 --i 元素并将 lim 减少到 len-2 一切都应该像以前一样工作,但它没有/为什么?这些数字实际上是相同的..
【问题讨论】:
-
注:
c可能在if (c!=EOF)中未定义lim <= 2。 -
Gaah,一个包含
getchar()的循环,其中包含对getchar()的条件调用......这不是最好的方法。每次迭代读取一个字符。 -
您是否尝试过使用调试器单步执行? (或者只是添加一些打印语句来跟踪执行。)
-
@chux 如果我明白你的意思,我会假设 lim 永远不会设置为小于 2(因为整个事情是如何工作的)
-
@unwind 是的,它看起来不太好,但这是有效的,因为它意味着丢弃字符(这样输出在单词之间不会有超过一个空格,并且制表符减少到一个空格)