从c中的标准输入读取到EOF

时间:2012-03-03 02:21:47

标签: c fread

我正在使用Unix机器,我试图从控制台读取直到达到EOF(我正在使用Ctrl + D)。我正在使用fread_unlocked,对于输入读取,它输出读取整数correclty但不是正常退出,它给出了EOF的分段错误。如何修改我的代码以使其按预期运行?

int MAXX = 10000000;
char *ipos, InpFile[MAXX];

inline int input_int(int flag=0)
{
  while(*ipos<=32)
    ++ipos;
 if(flag)
    return(*ipos++-'0');
 LL x=0,neg=0;
 char c;
 while(true)
  {
    c=*ipos++;
    if(c=='-')
        neg=1;
    else
    {
        if(c<=32)
         return neg?-x:x;x=(x<<1)+(x<<3)+c-'0';
    }
  }
 }
int main()
{
   ipos = InpFile;
   fread_unlocked(InpFile, MAXX, 1, stdin);
   while(true){
   int n = input_int();
   printf("%d\n",n);
   }
   return 0;
}   

我从控制台输入的内容是:3 4 5 6Ctrl+D 我现在得到的输出是:3 4 5 6 Segmentation Error 预期输出:3 4 5 6 感谢。

2 个答案:

答案 0 :(得分:3)

fread_unlocked返回实际读取的字节数。您需要获取该返回值,并且您需要确保永远不会尝试使用InpFile以外的多个字符。例如,如果在全局范围内声明max_ipos,则可以写:

size_t bytes_read = fread_unlocked(InpFile, 1, MAXX, stdin);
// check for errors
max_ipos = &InpFile[bytes_read];

然后input_int需要检测何时ipos == max_ipos并在阅读*ipos之前终止。

编辑添加:请注意(根据Jonathan Leffler的建议)我已将参数1MAXX的顺序切换为fread_unlocked 。这是因为您想要读取大小为1的对象,而不是大小为MAXX的对象。

顺便说一下,这个:

inline int input_int(int flag=0)

无效C.参数的默认值是C ++的东西。 (也许有C编译器支持它作为扩展 - 我不知道 - 但肯定有C编译器没有。)

答案 1 :(得分:0)

你的代码是非常脏的代码,每个人都要阅读它,确定,会混淆,所以,我清理你的代码:

#include <stdio.h>
#include <iostream>
using namespace std;
int MAXX = 10000000;
char x = 0 ; 
char *ipos = &x, InpFile[10000000];

inline int input_int(int flag=0){
  while( *::ipos <= 32 )
    ++::ipos;
  if(flag)
     return(*::ipos++) -'0';
  char x = 0 , neg = 0;
  char c = ' ';
  while ( true ) {
      c = (*::ipos++);
      if(c == '-')
          neg = 1;
      else {
          if(c <= 32)
              return neg ? -x : x; 
          x = (x << 1) + (x << 3) + c -'0';
      }
  }
}

int main(){
   ipos = InpFile;
   fread_unlocked(InpFile, MAXX, 1, stdin);
   while ( true ) {
       int n = input_int();
       printf( " %d \n " , n);
   }
   return 0;
}   

顺便说一句,你没有提到你的课程。 另一个问题:你没有初始化你的指针。如果你想使用指针,不要忘记初始化它们。