支持管道(一个有用的Hello World) 我试图写一个简单的C++程序集合,它遵循基本UNIX哲学: 让每个程序都做好一件事 期望每个程序的输出成为另一个未知程序的输入
我遇到了一个问题,试图将其中一个的输出作为另一个的输入,而将其中一个的输出作为其自身单独实例的输入。非常简单,我有一个程序add,它接受参数并给出求和结果。我希望能够通过管道将输出传输到另一个add实例支持管道(一个有用的Hello World) 我试图写一个简单的C++程序集合,它遵循基本UNIX哲学: 让每个程序都做好一件事 期望每个程序的输出成为另一个未知程序的输入,c++,unix,command-line,pipe,stdin,C++,Unix,Command Line,Pipe,Stdin,我遇到了一个问题,试图将其中一个的输出作为另一个的输入,而将其中一个的输出作为其自身单独实例的输入。非常简单,我有一个程序add,它接受参数并给出求和结果。我希望能够通过管道将输出传输到另一个add实例 ./add 1 2 | ./add 3 4 这将产生10,但目前产生7 我遇到了两个问题: cin等待来自控制台的用户输入。我不想这样,而且在没有在控制台中查询用户的情况下,无法找到一个简单的示例来演示标准输入流的使用。如果有人知道一个例子,请让我知道 我不知道如何在支持管道的同时使用标准输入
./add 1 2 | ./add 3 4
这将产生10,但目前产生7
我遇到了两个问题:
// ... COMMAND LINE PROCESSING ...
std::vector<double> numbers = multi.getValue(); // using TCLAP for command line parsing
if (numbers.size() > 0)
{
double sum = numbers[0];
double arg;
for (int i=1; i < numbers.size(); i++)
{
arg = numbers[i];
sum += arg;
}
std::cout << sum << std::endl;
}
else
{
double input;
// right now this is test code while I try and get standard input streaming working as expected
while (std::cin)
{
std::cin >> input;
std::cout << input << std::endl;
}
}
// ... MORE IRRELEVANT CODE ...
/。。。命令行处理。。。
std::vector number=multi.getValue();//使用TCLAP进行命令行解析
如果(numbers.size()>0)
{
双和=数字[0];
双精氨酸;
对于(int i=1;i std::cout您可能会发现一个有用的函数是isatty()
,它告诉您文件描述符是否连接到交互式会话。您可以这样使用它:
if (!isatty(fileno(stdin))) {
while (std::cin) {
// ...
}
}
这将仅尝试从终端读取非交互式输入(意味着stdin从文件或管道重定向)。问题可能在于:
if (numbers.size() > 0)
如果您有任何参数,它会添加它们并忽略所有管道数据。因此当然/add 3
返回3-它有一个参数,因此它会忽略管道数据
您应该修复代码以添加这两个输入(如果给定了输入)还有参数,不是非此即彼。记住:命令行参数并不排除管道输入。我想说最简单的方法是忽略程序中从stdin
读取的内容。相反,只让程序读取参数,并像这样调用它:/add 1 2 | xargs./add 3 4
xargs
会将第一个add
的输出作为第二个add
的参数这是两个问题,其中一个问题相当模糊(Unix哲学问题)。实际上,你的问题是关于管道的,如果有好的例子。我建议将标题更改为匹配。你写它“returns 3”-这是哪3个?是来自add命令(在管道之前还是第二个add命令的参数之前?啊,很好的回答。这是第二个3。我也发布了./ADD12 |./ADD34,它会产生7。Re:您的更新:现在请参阅@gregHewgill的答案,了解如何确定您的程序是从管道还是从控制台读取。
if (!isatty(fileno(stdin))) {
while (std::cin) {
// ...
}
}
if (numbers.size() > 0)