linux 非阻塞shuru_linux非阻塞输入 - CSDN
  • linux非阻塞键盘输入

    2016-01-01 22:29:04
    linux常用输入函数scanf和getchar通常都是阻塞式的,如果用户没有输入,程序就一直停在那儿;输入内容后,还需要用户点回车;同时,用户输入的信息,会在屏幕上显示出来。 而某些时候,我们不期望这种阻塞发生,也...

    linux常用输入函数scanf和getchar通常都是阻塞式的,如果用户没有输入,程序就一直停在那儿;输入内容后,还需要用户点回车;同时,用户输入的信息,会在屏幕上显示出来。
    而某些时候,我们不期望这种阻塞发生,也不想要敲入的按键在屏幕上回显,我们希望这一切都由自己写的程序来控制,键盘被按下,我们能够立刻响应,而不需要额外输入回车。
    代码如下:

    #include<stdio.h>
    #include <stdlib.h>
    
    #define TTY_PATH            "/dev/tty"
    #define STTY_US             "stty raw -echo -F "
    #define STTY_DEF            "stty -raw echo -F "
    
    static int get_char();
    
    static int get_char()
    {
        fd_set rfds;
        struct timeval tv;
        int ch = 0;
    
        FD_ZERO(&rfds);
        FD_SET(0, &rfds);
        tv.tv_sec = 0;
        tv.tv_usec = 10; //设置等待超时时间
    
        //检测键盘是否有输入
        if (select(1, &rfds, NULL, NULL, &tv) > 0)
        {
            ch = getchar(); 
        }
    
        return ch;
    }
    
    int main()
    {
        int ch = 0;
        system(STTY_US TTY_PATH);
    
        while(1)
        {
            ch = get_char();
            if (ch)
            {
                printf("key = %d(%c)\n\r", ch, ch);
                switch (ch)
                {
                    case 3//ctrl+c
                        {system(STTY_DEF TTY_PATH);return 0;}
                    case '0':
                        printf("0\n\r");break;
                    case '1':
                        printf("1\n\r");break;
                    case '2':
                        printf("2\n\r");break;
                    case '3':
                        printf("3\n\r");break;
                }
            }           
        }
    }
    

    运行结果:
    这里写图片描述

    展开全文
  • 作者:fbysssmsn:jameslastchina@hotmail.com blog:blog.csdn.net/fbysss声明:本文由fbysss整理...问题2:在等待键盘输入的时候,程序被阻塞了,下面的代码必须在输入处理之后才能执行。如果不使用线程,如何实现

    作者:fbysss
    msn:jameslastchina@hotmail.com 
    blog:blog.csdn.net/fbysss
    声明:本文由fbysss整理编写,转载请注明出处
    关键字:getch
    问题1:标准c中没有getch函数,等待键盘输入之后,总是需要按下回车才能得到值,如何解决?
    问题2:在等待键盘输入的时候,程序被阻塞了,下面的代码必须在输入处理之后才能执行。如果不使用线程,如何实现非阻塞模式?
    解决办法:

    #include <curses.h>
    #include 
    <fcntl.h>
    int main()
    {
        
    int ch;

        WINDOW 
    * win=  initscr();              /* 开始curses模式  */
        scrollok(win,TRUE);                        
    /*设置屏幕可滚动,否则超出一屏之后显示不完全*/
         
    //raw();                              /* 禁用行缓冲   */
        keypad(stdscr, TRUE);               /* 开启功能键响应模式 */
        noecho();                           
    /* 当执行getch()函数的时候关闭键盘回显 */
        
    //fcntl(0,F_SETFL, O_NONBLOCK);//这句用于设置非阻塞模式。即在侦测键盘输入的同时,不影响getch后面语句的执行。本函数位于头文件fcntl.h中
        while(1){
        printw(
    "Type any character to see it in bold ");

        ch 
    = getch();                       /* 原注:如果没有调用raw()函数,必须按下enter键才可以执行下面的程序 
        实验结果表明,使用了raw()之后同样不需要回车就可以执行下去。另外,如果使用了raw(),ctrl+c也会被捕获
    */


        
    if(ch == KEY_F(1))                  /* 如果没有调用keypad()初始化,将不会执行这条语句 */
        
    {
        printw(
    "F1 Key pressed");       /* 如果没有使用 noecho() 函数,一些难看的控制字符将会被打印到屏幕上 */
        }

        
    else if(ch!=-1)
        
    {
        printw(
    "The pressed key is ");
          attron(A_BOLD);
          printw(
    "char:%c,intvalue:%d", ch,ch);
          attroff(A_BOLD);
        }

        refresh();                         
    /* 将缓冲区的内容打印到显示器上 */
    }



         endwin();                            
    /* 结束curses模式     */
         
    return 0;
    }

    注:用gcc编译的时候要注意一点,必须加上-lcurses参数,否则会出现undefined reference to `initscr'等等一大堆错误信息

    展开全文
  • #include &lt;iostream&gt; #include &lt;stdio.h&gt; #include &lt;unistd.h&gt; #include &lt;stdlib.h&gt; #include &lt;sys/ioctl.h&... //fd_set 为long型数组...
    #include <iostream>
    #include <stdio.h>
    #include <unistd.h>  
    #include <stdlib.h>  
    #include <sys/ioctl.h>  
    using namespace std;
    
    
    char GetInput()
    {
        //fd_set 为long型数组
        //其每个元素都能和打开的文件句柄建立联系
        fd_set rfds;
        struct timeval tv;
        char c = '\0';
    
        //将 rfds数组清零
        FD_ZERO(&rfds);
        //将rfds的第0位置为1,这样fd=1的文件描述符就添加到了rfds中
        //最初 rfds为00000000,添加后变为10000000
        FD_SET(0, &rfds);
        tv.tv_sec = 1;
        tv.tv_usec = 0; //设置等待超时时间
    
        //检测键盘是否有输入
        //由内核根据io状态修改rfds的内容,来判断执行了select的进程哪个句柄可读
        if (select(1, &rfds, NULL, NULL, &tv) > 0)
        {
            c = getchar();
    
            return c;
        }
    
        //没有数据返回n
        return 'n';
    }
    
    
    
    int main()
    {
        //关闭缓存区,使从终端接收一个字符不用按回车
        system("stty -icanon"); 
        while(1)
        {
    
            char c = GetInput();
            
            if('n'==c)
            {
                cout<<"no data"<<endl;
            }
            else
            {
                cout<<endl<<"c  = "<<c<<endl;
            }
            
        }
        
        
        return 0;
        
    }
    
    
    

    展开全文
  • Linux阻塞与非阻塞

    2019-05-13 22:22:28
    1.阻塞(block)概念:指进程或线程在执行设备操作或管道,或则网络时,不能获取到...2.非阻塞(non_block):进程就算没有获取到资源或没有等到事件发生时不挂起,通常会直接放弃或不断查询, 直到可以进行的位置。也就...

    1.阻塞(block)概念:指进程或线程在执行设备操作或管道,或则网络时,不能获取到资源就被挂起,
    直到满足可操作的条件后在进行操作,被挂起的进程进入休眠状态,从运行队列移走,直到
    等待的条件满足才继续执行。也就是执行到某些函数时必须等待某个事件发生函数才返回。
    2.非阻塞(non_block):进程就算没有获取到资源或没有等到事件发生时不挂起,通常会直接放弃或不断查询,
    直到可以进行的位置。也就是函数的执行不必等待事件发生,一旦执行肯定返回,用返回值来反应函数执行情况。
    3.例如:read读取输入输出设备/dev/tty

    4.read设备文件时发生阻塞

    #include<sys/types.h>
    #include<sys/stat.h>
    #include<fcntl.h>
    #include<unistd.h>
    #include<stdio.h>
    #include<stdlib.h>
    
    int main(int argc, char* argv[])
    {
        int fd = open("/dev/tty",O_RDONLY); //打开标准输入输出文件,此时为阻塞
        if(fd == -1){
            perror("open /dev/tty");
            exit(1);
        }
        int ret = 0;
        char buf[1024] = {0};
        while(1){
            ret = read(fd, buf, sizeof(buf));
            if(ret == -1){
                perror("read");
                exit(1);
            }
            else if(ret == 0)
                printf("buf is null\n");
            else if(ret > 0)
                printf("buf is %s\n",buf);
            printf("test\n");
            sleep(1);
        } 
        close(fd);
    
        return 0;
    }
    

    5.直接用O_NONBLOCK设置非阻塞

    int main(int argc, char* argv[])
    {
        int fd = open("/dev/tty", O_RDONLY | O_NONBLOCK); // O_NONBLOCK 设置文件输入输出为非阻塞
        if(fd == -1){
            perror("open /dev/tty");
            exit(1);
        }
        int ret = 0;
        char buf[1024] = {0};
        while(1){
            ret = read(fd, buf, sizeof(buf));
            if(ret == -1){
                perror("read /dev/tty");
                printf("no input,buf is null\n");
            }
            else {
                printf("ret = %d, buf is %s\n",ret, buf);
            }
            sleep(1);
        }
        close(fd);
    
        return 0;
    }
    

    6.用fcntl()函数与O_NONBLOCK设置非阻塞

    int main(int argc, char* argv[])
    {
        int fd = open("/dev/tty", O_RDONLY);
    
        //fcntl()函数设置标准输入输出文件为非阻塞
        int flag = fcntl(fd, F_GETFL);  //第一步:获取文件操作权限
        flag |= O_NONBLOCK;       //第二步:获取的文件属性与O_NONBLOCK相或
        fcntl(fd, F_SETFL, flag); //第三步:再次设置文件操作权限
        int ret = 0;
        char buf[1024] = {0};
        
        while(1){
            ret = read(fd, buf, sizeof(buf));
            if(ret == -1){
                perror("read /dev/tty");
                printf("no input,buf is null\n");
            }
            else {
                printf("ret = %d, buf is %s\n",ret, buf);
            }
            sleep(1);
        }
        close(fd);
    
        return 0;
    }
    
    展开全文
  • 本文为windows和Linux系统下,对键盘输入进行实时监听的方法,为非阻塞 Windows下c代码 #include <conio.h> #include <windows.h> #include <iostream> using namespace std; int main() { ...
  • 非阻塞式I/O包括非阻塞输入操作,非阻塞输出操作,非阻塞接收外来连接,非阻塞发起外出连接。包括的函数有:read, readv, recv, recvfrom, recvmsg, write, writev, send, sendto, sendmsg, accept。 将socket 设置...
  • 很久很久以前,系windows平台下,用C语言写过一款贪食蛇游戏,cmd界面,用kbhit()函数实现非阻塞输入。系windows平台下用python依然可以调用msvcrt.khbit实现非阻塞监听。但系喺linux下面就冇呢支歌仔唱。  随手...
  • 阻塞socket和非阻塞socket的区别读操作对于阻塞的socket/recv,当socket的接收缓冲区中没有数据时,read调用会一直阻塞住,直到有数据到来才返回。当socket缓冲区中的数据量小于期望读取的数据量时,返回实际读取的...
  • 阻塞和非阻塞 读常规文件是不会阻塞的,不管读多少字节,read一定会在有限的时间内返回。从终端设备或网络读则不一定,如果从终端输入的数据没有换行符,调用read读终端设备就会阻塞,如果网络上没有接收到数据包,调用...
  • 所谓非阻塞方式non-block,就是进程或线程执行此函数时不必非要等待事件的发生,一旦执行肯定返回,以返回值的不同来反映函数的执行情况,如果事件发生则与阻塞方式相同,若事件没有发生则返回一个代码来告知事件未...
  • 参考文章: 关于有名管道open时阻塞的问题 Linux有名管道(FIFO)的阻塞和非阻塞读写 挖坑,日后填 转载于:https://www.cnblogs.com/kelamoyujuzhen/p/9691634.html
  • 阻塞读终端:block指当串口输入缓冲区没有数据的时候,read函数将会阻塞在这里,移植到串口输入缓冲区中有数据可读取,read读到了需要的字节数之后,返回值为读到的字节数 #include <unistd.h> #include <...
  • linux C socket编程 — 阻塞式与非阻塞式 阻塞和非阻塞  阻塞函数在完成其指定的任务以前不允许程序调用另一个函数。例如,程序执行一个读数据的函数调用时,在此函数完成读操作以前将不会执行下一程序语句...
  • TCP连接函数用于连接服务器端口,若服务器地址不存在时,并不能在短时间内返回连接结果; 非阻塞connect接口主要用于控制连接的时间,防止异常连接带来的过长的CPU占用;
  • 阻塞、非阻塞 读常规文件是不会阻塞的,不管读多少字节,read一定会在有限的时间内返回。从终端设备或网络读则不一定,如果从终端输入的数据没有换行符,调用read读终端设备就会阻塞,如果网络上没有接收到数据包,...
  • Select在Socket编程中还是比较重要的,可是对于初学Socket的人来说都不太爱用Select写程序,他们只是习惯写诸如 connect、accept、recv或recvfrom这样的阻塞程序(所谓...可是使用Select就可以完成非阻塞(所谓非阻塞
  • 本文整理转自:... 会阻塞的函数:connect, accept,send/recv/sendto/recvfrom等读写函数. 不会阻塞的函数:bind, listen,socket, closesocket. ...linux网络通信模型有: ...阻塞IO模型(同步),非阻塞IO模型
  • #include #include #include #include #include #include static struct termios ori_attr, cur_attr; //static __inline int tty_reset(void) { if (tcsetattr(STDIN_FILENO, TCSANOW, &ori_attr) !...
  • 有两个可以进行控制串口阻塞性... 对于read,block指当串口输入缓冲区没有数据的时候,read函数将会阻塞在这里,移植到串口输入缓冲区中有数据可读取,read读到了需要的字节数之后,返回值为读到的字节数; 对于w
  • 1.阻塞与非阻塞1.1 阻塞的定义对于read,指当串口输入缓存区没有数据的时候,read函数将会阻塞在这里,直到串口输入缓存区中有数据可读取,read读到了需要的字节数之后,返回值为读到的字节数;对于write,指当串口...
1 2 3 4 5 ... 20
收藏数 45,567
精华内容 18,226
关键字:

linux 非阻塞shuru