C++ getline cin 问题

标签 c++ getline cin

 while (true)
 {
    int read = recvData(clientSocket, buf, sizeof(buf));
    if(read == SOCKET_ERROR)
    {
        cout<<"Connection with the server is lost. Do you want to exit?" << endl;
        string input;
        getline(cin,input);
        if(input == "yes")
            cout<<"test";
    }
    if(read == SHOW )
    {
        char *p = strtok(buf, " ");
        while (p) 
        {
            cout<<p<<endl;
            p = strtok(NULL, " ");
        }
    }

    else if(read == SEND )
    {
        UDPinfo* info = new UDPinfo;
        char *p = strtok(buf, " ");
        info->_IP = p;
        p = strtok(NULL, " ");
        info->_Port= p;
        info->_filePath = filePath;
        info->_UPDsock = UDPSocket;
        //Starting UDP send thread.
        _beginthread(UDPsendThread, 0, (void*)info);
    }
  }

在这个例子中,如果我得到一个套接字错误,我会友好地询问用户是否想通过获取输入来退出程序。然后将该输入与其他值进行比较,在这种情况下它是一个"is"字符串。但出于某种原因,即使我输入"is",它也会跳过 if 检查。并打印“与服务器的连接丢失。你想退出吗?”再次。奇怪的是,如果我再次输入"is",它就会起作用。我尝试使用 cin.ignore(); 修复它以及所有这些东西,但没有解决方案。

最佳答案

好吧,如果你输入 yes,你似乎没有办法退出循环,它只是打印 test 并继续它的快乐方式,试图阅读更多数据。

如果你的意思是第一次输入yes时它不打印test那么你需要临时更改:

getline(cin,input);

到:

getline (cin, input);
cout << "[" << input << "]" << endl;

当您比较缓冲区时,尝试找出该缓冲区中的实际内容。


就其值(value)而言,这段代码(与您的代码非常相似)工作正常:

#include <iostream>

int main (void) {
    while (true) {
        int read = -1;
        if (read == -1) {
            std::cout << "Connection lost, exit?" << std::endl;
            std::string input;
            getline (std::cin, input);
            std::cout << "[" << input << "]" << std::endl;
            if (input == "yes") {
                std::cout << "You entered 'yes'" << std::endl;
                break;
            }
        }
        std::cout << "Rest of loop" << std::endl;
    }
    return 0;
}

您还应该意识到您的逻辑存在漏洞。当您在缓冲区上执行 strtok 时,它会修改缓冲区并为您提供指向它的指针(即实际缓冲区)。它不会为您制作拷贝。

如果您随后将这些指针保存在 info 中并将其传递给另一个线程,同时您返回并将更多信息读入该缓冲区,那么您的主线程和您将信息传递到的线程将发生冲突。很糟糕。

如果您必须使用strtok 来获取信息,请确保您strdup 它并将拷贝 传递给您的其他线程(记住完成后释放它们)。大多数 C 实现都有一个 strdup(虽然它不是 ISO 标准)。如果您没有,请参阅 here .

这个漏洞很有可能会导致您的奇怪行为。

解决此问题的最佳方法是更改​​以下两行:

    info->_IP = p;
    info->_Port= p;

进入:

    info->_IP = strdup (p);
    info->_Port= strdup (p);

并记住在你的另一个线程完成时释放这两个内存分配(通常我不会提倡 C++ 的 malloc 类型的操作,但是,因为你已经在使用字符缓冲区而不是字符串,这似乎是最简单的解决方案。

关于C++ getline cin 问题,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/6605865/

相关文章:

c++ - 跳过 cin.get() 和 cin.ignore()

c++ - cin.getline() 没有按预期工作

c++ - 带有无符号tickCount/Wrapping的耗时

C++类和对象——内存

C++ 存储 cin 输入并跳过其他输入

C++ getline cin错误

c - 通过 socket tcp 发送一个带有空格的字符串

c++ - Linux/Unix 中的 futex 有什么等价物吗?

c++ - 模拟退火算法

haskell - 将用户输入(整数)转换为条件打印语句