Reputation: 1166
I want to write NodeJS code for solving problems like ICPC. The following is an example using a template of www.hackerrank.com for submitting in JavaScript:
process.stdin.resume();
process.stdin.setEncoding('ascii');
var input_stdin = "";
var input_stdin_array = "";
var input_currentline = 0;
process.stdin.on('data', function (data) {
input_stdin += data;
});
process.stdin.on('end', function () {
input_stdin_array = input_stdin.split("\n");
main();
});
function readLine() {
return input_stdin_array[input_currentline++];
}
/////////////// ignore above this line ////////////////////
function main() {
var s = readLine();
s = s.split(",");
s = s.join(" ");
process.stdout.write(s);
}
I want to code offline, so I need to run the programs in my Windows console. For runnig the srcript using C:users\user>node path\file.js I added at the end of the code the line
main();
and the scripts runs, but it doesn't process the standard input. It gives me and error in "s=s.split()", the error is the following "TypeError: Cannot read property 'split' of undefined". If anyone know how to do node process the standard input please help me.
Upvotes: 2
Views: 6270
Reputation: 5088
You can wait for SIGINT
, The SIGINT
event is emitted whenever the input stream receives a CTRL+C input, known typically as SIGINT
. If there are no SIGINT
event listeners registered when the input stream receives a SIGINT
, the pause event will be emitted.
When SIGINT
is received, your main()
function will be called and after returning, The process.exit()
will close the process.
So instead of waiting for end event
process.stdin.on('end', function(){
input_stdin_array = input_stdin.split("\n");
main();
});
You can wait for 'SIGINT' as below:
process.on('SIGINT', function(){
input_stdin_array = input_stdin.split("\n");
main();
process.exit();
});
Upvotes: 5
Reputation: 2195
run the script using node js
node file.js
then start typing your input on the console.
once done hit Cntrl+C and the code written in the SIGINT process are executed.
have made the following changes in the code
process.stdin.resume();
process.stdin.setEncoding('ascii');
var input_stdin = "";
var input_stdin_array = "";
var input_currentline = 0;
process.stdin.on('data', function (data) {
input_stdin += data;
});
process.stdin.on('end', function () {
input_stdin_array = input_stdin.split("\n");
main();
});
process.on('SIGINT', function(){
input_stdin_array = input_stdin.split("\n");
main();
process.exit();
});
function readLine() {
return input_stdin_array[input_currentline++];
}
/////////////// ignore above this line ////////////////////
function main() {
var s = readLine();
s = s.split(",");
s = s.join(" ");
process.stdout.write(s);
}
Upvotes: 2
Reputation: 30685
I'd suggest you modify your code to append to an array with each line rather than creating one long string and then splitting it. e.g.
process.stdin.resume();
process.stdin.setEncoding('ascii');
var input_stdin_array = [];
var input_currentline = 0;
process.stdin.on('data', function (data) {
input_stdin_array.push(data);
});
process.stdin.on('end', function () {
main();
});
function readLine() {
if (input_currentline >= input_stdin_array.length) {
return "";
}
return input_stdin_array[input_currentline++];
}
/////////////// ignore above this line ////////////////////
function main() {
do
{
var line = readLine();
console.log("Line: " + line)
} while ((line||"") !== "")
}
In addition, as the other answer says, you want to listen to 'SIGINT' rather than 'end'.
I'd also suggest using the Readline module, like so:
var readline = require('readline');
var reader = readline.createInterface({
input: process.stdin,
output: process.stdout,
terminal: true
});
var lines = [];
reader.on('line', function (line) {
lines.push(line);
});
reader.on('close', function (line) {
console.log('All done:');
console.log('Lines: ', lines);
});
You can trigger 'close' using CTRL-D.
Upvotes: 4