【问题标题】:Cannot trigger 'end' event using CTRL D when reading from stdin从标准输入读取时无法使用 CTRL D 触发“结束”事件
【发布时间】:2022-04-02 16:33:58
【问题描述】:

在下面的代码中

process.stdin.resume();
process.stdin.setEncoding('utf8');

process.stdin.on('data', function(chunk) {
  process.stdout.write('data: ' + chunk);
});

process.stdin.on('end', function() {
  process.stdout.write('end');
});

我无法使用ctrl+D触发'end'事件,而ctrl+C直接退出而不触发。

hello
data: hello
data
data: data
foo
data: foo
^F
data: ♠
^N
data: ♫
^D
data: ♦
^D^D
data: ♦♦

【问题讨论】:

  • 我正在 Mac Catalina、NodeJS 12.16.2 上进行测试,可以确认 CTRL+D 可以正常使用您的代码

标签: node.js events stdin


【解决方案1】:

我会改变这个(组合键Ctrl+D):

process.stdin.on('end', function() {
    process.stdout.write('end');
});

对此(组合键Ctrl+C):

process.on('SIGINT', function(){
    process.stdout.write('\n end \n');
    process.exit();
});

更多资源:process docs

【讨论】:

  • 你使用的是什么版本的 Node.js?
  • 我不确定为什么部分。我环顾四周,没有看到任何明显的建议。我的猜测是 stdin.on 没有收到结束事件,因此它从不调用它。但同样,这只是一个猜测。
【解决方案2】:

我也遇到了这个问题,在这里找到了答案:Github issue

windows本身提供的readline接口(比如你现在使用的那个)不支持^D。如果您想要更多 unix-y 行为,请使用 readline 内置模块并将 stdin 设置为原始模式。这将使节点解释原始按键并且 ^D 将起作用。见http://nodejs.org/api/readline.html

如果您在 Windows 上,readline 界面默认不支持 ^D。您需要根据链接的说明进行更改。

【讨论】:

  • 你建议用什么替代?
【解决方案3】:

如果您是在 Hackerrank 代码对工具的上下文中执行此操作,那么这是给您的。

工具的工作方式是您必须在 Stdin 部分输入一些输入,然后单击 Run 将带您进入 stdout。

在标准输入中输入的所有输入行都将由代码的 process.stdin.on("data",function(){}) 部分处理,并且一旦输入“结束”,它将直接进行到 process.stdin.on("end", function(){}) 部分,我们可以在其中进行处理并使用 process.stdout.write("") 将结果输出到 Stdout。

process.stdin.resume();
process.stdin.setEncoding("ascii");
var input = "";
process.stdin.on("data", function (chunk) {
    // This is where we should take the inputs and make them ready.
    input += (chunk+"\n");
    // This function will stop running as soon as we are done with the input in the Stdin
});
process.stdin.on("end", function () {
    // When we reach here, we are done with inputting things according to our wish.
    // Now, we can do the processing on the input and create a result.
    process.stdout.write(input);
});

您可以通过将上面的代码粘贴到代码窗口中来检查流程。

【讨论】:

  • 它没有触发 process.stdin.on("end") 事件。你能帮我解决这个问题吗?
【解决方案4】:

或者

  1. 使用包含测试数据的输入文件,例如输入.txt
  2. 将您的 input.txt 传送到节点

猫输入.txt |节点 main.js

【讨论】:

    【解决方案5】:

    我在 Mac 上使用 IntelliJ IDEA 调试 Hackerrank 代码时也遇到过这种情况。 需要说的是,没有 IDEA,在终端中执行完全相同的命令 - 一切正常。

    起初,我发现了这个:IntelliJ IDEA: send EOF symbol to Java application - 令人惊讶的是,Cmd+D 工作正常并发送 EOF。

    然后,深入IDEA设置,我发现“其他->发送EOF”,默认是Cmd+D。添加第二个快捷方式后 (Ctrl+D) - 一切正常。

    【讨论】:

    • 注意可能会影响之前Idea的快捷方式;例如Ctrl+D 运行 Debug
    • 对于那些在 Idea / WebStorm 上测试 Hackerrank 的人,你可能需要Edit Configuration... 并添加环境变量,例如OUTPUT_PATH=./output.txt
    【解决方案6】:

    如果你想在你的windows pc上使用node运行程序,你也可以尝试这样的事情,这里我已经使用ctrl+d触发结束,希望对你有帮助

    
    'use strict';
    const { METHODS } = require('http');
    const readline = require('readline')
    process.stdin.resume();
    process.stdin.setEncoding('utf-8');
    readline.emitKeypressEvents(process.stdin);
    let inputString = '';
    let currentLine = 0;
    process.stdin.setRawMode(false)
    process.stdin.on('data', inputStdin => {
        inputString += inputStdin;
    });
    process.stdin.on('keypress', (str, key) => {
        if (key && key.ctrl && key.name == 'd'){
            inputString = inputString.trim().split('\n').map(string => {
                return string.trim();
            })
            main();  
        }
    });
    function readLine() {
        return inputString[currentLine++];
    }
    function method() {
    
    }
    function main() {
        const n = parseInt(readLine().trim());
        const arr = readLine().replace(/\s+$/g, '').split(' ').map(qTemp =>parseInt(qTemp,10))
        method();
    }
    
    
    

    【讨论】:

    • 您的答案可以通过额外的支持信息得到改进。请edit 添加更多详细信息,例如引用或文档,以便其他人可以确认您的答案是正确的。你可以找到更多关于如何写好答案的信息in the help center
    【解决方案7】:

    您可以使用 redirectionoperator 提供来自文件的输入

    $ node main.js < input.txt
    


    [仅适用于基于 Unix 的机器,例如 MacBook、Linux...]

    或者,在 shell 中输入输入后,您可以按 Ctrl + D 发送 EOF(end-of-file) 以触发 process.stdin.on("end", ...) 中的事件处理程序

    @Mark提到的Microsoft Windows默认不支持Ctrl+D(^D)

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2017-09-07
      • 1970-01-01
      • 1970-01-01
      • 2020-09-12
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多