C 从EOL中删除字符

C 从EOL中删除字符,c,linux,newline,C,Linux,Newline,我从串行设备读取缓冲区。它返回这些结果(每次2行) 这些结果在Linux命令行中^M^J是EOL,在Windows中表示\r\n。第一个结果还可以,但另外两个结果很糟糕。有没有办法检查^M^J个字符并将其删除?因为我想要这些结果: Hello World. My name is John. Hello World. My name is Mike. Hello World. My name is Peter. 使用此代码,我读取缓冲区 char buff[150]; memset(buff

我从串行设备读取缓冲区。它返回这些结果(每次2行)

这些结果在Linux命令行中^M^J是EOL,在Windows中表示\r\n。第一个结果还可以,但另外两个结果很糟糕。有没有办法检查^M^J个字符并将其删除?因为我想要这些结果:

Hello World.
My name is John.

Hello World.
My name is Mike.

Hello World.
My name is Peter.
使用此代码,我读取缓冲区

char buff[150];
memset(buff, 0, sizeof(buff));
for (;;)
{
  n=read(fd,buff,sizeof(buff));
  printf("%s", buff);
}
更新

我以这种方式打开并配置我的设备

int open_port(void)
{
int fd; // file description for the serial port 
fd = open("/dev/ttyAMA0", O_RDWR | O_NOCTTY | O_NDELAY);
if(fd == -1) // if open is unsucessful
{
 //perror("open_port: Unable to open /dev/ttyAMA0 - ");
 printf("open_port: Unable to open /dev/ttyAMA0. \n");
}
else
{
  fcntl(fd, F_SETFL, 0);
  printf("port is open.\n");
}

return(fd);
} //open_port
并配置端口

int configure_port(int fd)      // configure the port
{
 struct termios port_settings;      // structure to store the port settings in
 cfsetispeed(&port_settings, B9600);    // set baud rates
 cfsetospeed(&port_settings, B9600);
 port_settings.c_cflag &= ~PARENB;    // set no parity, stop bits, data bits
 port_settings.c_cflag &= ~CSTOPB;
 port_settings.c_cflag &= ~CSIZE;
 port_settings.c_cflag |= CS8;
 tcsetattr(fd, TCSANOW, &port_settings);    // apply the settings to the port
 return(fd);

} //configure_port

首先,
^M^J
是行的结尾,而不是文件的结尾

其次,
read
从指定的文件描述符读取二进制数据。它读取您指定的字符数,直到到达文件末尾或出现错误为止。如果您想一次读取行,一次读取一个字节,或者使用其他面向行的I/O调用(sscanf,诸如此类)

您可以查看问题,它提出了一个函数,用于从文件中读取行并处理Windows的回车。

The
printf()当它看到一个
\r\n
而不是一个单独的
\n
时,它的行为非常有趣。它将成对字符的行尾解释为非行尾,因此它不执行通常的行尾函数,而是向您显示一个
^M^J
。简单地消除
\r
将为您提供所需的行为

  char buff[150];
  int n = read(fd,buff,sizeof(buff));  // buff is not NUL terminated
  if (n < 0) {
    // deal with I/O error
    }
  if (n == 0) {
    // deal with end-of-file
    }
  else {
    for (int i=0; i<n; i++) {
      if (isprint(buff[i]) || (buff[i] == '\n')) {
        putchar(buff[i]);
      }
      else if (buff[i] == '\r') {
        ; // drop it
      }
      else {
        ; // TBD deal with unexpected control codes and codes 127-255
      }
    }
  }
charbuff[150];
int n=读取(fd,buff,sizeof(buff));//buff不是NUL终止的
if(n<0){
//处理I/O错误
}
如果(n==0){
//处理文件末尾
}
否则{

对于(int i=0;i打开带有
O_文本的文件

#include <fcntl.h>
fd = open("/dev/ttyAMA0", O_RDWR | O_NOCTTY | O_NDELAY | O_TEXT);
#包括
fd=打开(“/dev/ttyam0”,O|RDWR | O|NOCTTY | O|NDELAY | O|TEXT);

我认为您必须逐字符检查ascii值,在您读取()之后windows中会发生什么
EOF?读会停止吗?我不知道Windows会发生什么。我使用Linux,我有这些characters@mf_很明显,EOF是EOL的错别字。我们的,敲我的头,答案被删除,对不起。谢谢你的回答。我用开放和配置函数更新了帖子,我写了一个问题,因为我得到的fd是int,我能用它来处理fgets吗?我想nk否!我在您的更新中看到了这一点,并将修改我的答案。(应该在原始的
read()
)使用此解决方案(使用此标题)时看到它)我有错误:“O_TEXT”未在此范围内声明。或者1)
O_TEXT
位于包含文件中,例如
,或2)
,或者您使用的是类Unix系统,不区分二进制文件和文本文件。如果是#2,并且发出消息的单元类似PC,则应使用O_TEXT标志。
#include <fcntl.h>
fd = open("/dev/ttyAMA0", O_RDWR | O_NOCTTY | O_NDELAY | O_TEXT);