繁体   English   中英

node.js 中“process.stdout.write”和“console.log”的区别?

[英]Difference between "process.stdout.write" and "console.log" in node.js?

node.js 中的“process.stdout.write”和“console.log”有什么区别?

编辑:对变量使用 console.log 时显示了很多不可读的字符,而使用 process.stdout.write 显示了 object。

这是为什么?

console.log()调用带有格式化输出的process.stdout.write 有关实现,请参阅 console.js 中的format()

目前(v0.10.ish):

Console.prototype.log = function() {
  this._stdout.write(util.format.apply(this, arguments) + '\n');
};

查看 Node 文档,显然 console.log 只是 process.stdout.write ,最后有一个换行符:

console.log = function (d) {
  process.stdout.write(d + '\n');
};

来源: http : //nodejs.org/docs/v0.3.1/api/process.html#process.stdout

我知道这是一个非常古老的问题,但我没有看到有人谈论process.stdout.writeconsole.log之间的主要区别,我只想提一下。

正如Mauvis LefordTK-421指出的那样, console.log line-break尾( \\n )添加了一个line-break但这并不是它所做的全部。

代码至少从0.10.X版本开始没有改变,现在我们有了5.X版本。

是代码:

Console.prototype.log = function() {
  this._stdout.write(util.format.apply(this, arguments) + '\n');
};

正如你所看到的,有一个部分说.apply(this, arguments)并且它在功能上有很大的不同。 用例子更容易解释:

process.stdout.write有一个非常基本的功能,你可以在里面写一些东西,像这样:

process.stdout.write("Hello World\n"); 

如果您不将换行符放在最后,您的字符串后面会出现一个奇怪的字符,如下所示:

process.stdout.write("Hello World"); //Hello World% 

(我认为这意味着类似于“程序的结尾”,因此只有在文件末尾使用了process.stdout.write并且没有添加中断行时,您才会看到它)

另一方面, console.log可以做更多的事情。

  1. 你可以用同样的方式使用它

    console.log("Hello World"); //You don't need the break line here because it was already formated console.log("Hello World"); //You don't need the break line here because it was already formated ,而且那个奇怪的字符也消失了

  2. 你可以写多个字符串

    console.log("Hello", "World");

  3. 你可以建立关联

    console.log("Hello %s", "World") //Useful when "World" is inside a variable

就是这样,多亏了util.format.apply部分(我可以谈论很多关于这到底是做什么的,但你明白我的意思,你可以在这里阅读更多)。

我希望有人觉得这些信息有用。

一个尚未提及的重大区别是process.stdout只接受字符串作为参数(也可以是管道流),而console.log接受任何 Javascript 数据类型。

例如:

// ok
console.log(null)
console.log(undefined)
console.log('hi')
console.log(1)
console.log([1])
console.log({one:1})
console.log(true)
console.log(Symbol('mysymbol'))

// any other data type passed as param will throw a TypeError
process.stdout.write('1')

// can also pipe a readable stream (assuming `file.txt` exists)
const fs = require('fs')
fs.createReadStream('file.txt').pipe(process.stdout)

这种情况下的另一个重要区别是process.stdout.clearLine()process.stdout.cursorTo(0)

如果您只想在一行中显示下载或处理的百分比,这将非常有用。 如果您将 clearLine()、cursorTo() 与console.log()则它不起作用,因为它还会将 \\n 附加到文本中。 试试这个例子:

var waitInterval = 500;
var totalTime = 5000;
var currentInterval = 0;

function showPercentage(percentage){
    process.stdout.clearLine();
    process.stdout.cursorTo(0);
    console.log(`Processing ${percentage}%...` ); //replace this line with process.stdout.write(`Processing ${percentage}%...`);
}

var interval = setInterval(function(){
 currentInterval += waitInterval;
 showPercentage((currentInterval/totalTime) * 100);
}, waitInterval);

setTimeout(function(){
 clearInterval(interval); 
}, totalTime);

在获得 https.request for post 方法的帮助后,我刚刚在研究这个问题时注意到了一些事情。 我想我分享一些输入来帮助理解。

process.stdout.write不会在console.log添加新行,就像其他人提到的那样。 但也有这个更容易用例子来解释。

var req = https.request(options, (res) => {
    res.on('data', (d) => {
        process.stdout.write(d);
        console.log(d)
    });
});

process.stdout.write(d); 将正确打印数据而无需换行。 然而, console.log(d)将打印一个新行,但数据不会正确显示,例如给出这个<Buffer 12 34 56...

为了使console.log(d)正确显示信息,我必须这样做。

var req = https.request(options, (res) => {
    var dataQueue = "";    
    res.on("data", function (d) {
        dataQueue += d;
    });
    res.on("end", function () {
        console.log(dataQueue);
    });
});

所以基本上:

  • process.stdout.write连续打印信息作为正在检索的数据并且不添加新行。

  • console.log打印在检索点获得的信息并添加一个新行。

这是我能解释的最好方法。

简单的区别是: console.log()方法自动附加换行符。 这意味着如果我们循环并打印结果,每个结果都会打印在新行中。

process.stdout.write()方法不附加换行符。 用于打印图案。


Console.log 实现 process.sdout.write,process.sdout.write 是一个缓冲区/流,将直接输出到您的控制台中。

根据我的 puglin serverlineconsole = new Console(consoleOptions)你可以用你自己的readline系统重写 Console 类。

可以看到console.log的代码源:


查看更多:

对于喜欢Deno 的人,我可以通过使用以下ANSI 转义序列和 Deno 的process.stdout.write版本来实现这一点。

ESC[2K  clears entire line
ESC[#G  moves cursor to column #

代码

/*
    Console.log() to the same line
    Supported in Deno 1.8.1
*/

const myTextEncoder : TextEncoder = new TextEncoder();

let counter : number = 0;

while(counter < 100000) {

  // ESC[2K clears entire line
  await Deno.stdout.write(myTextEncoder.encode(`\x1b[2K`));
  // ESC[#G moves cursor to column #
  await Deno.stdout.write(myTextEncoder.encode(`\x1b[0G`));
  // OUTPUT incremented counter
  await Deno.stdout.write(myTextEncoder.encode(`COUNTER: ${counter++}`));

}

每次调用console.log()时都会添加大量内容和新行

process.stdout.write()只是纯文本,没有格式

至少这是我被教导的

这里的答案很棒。 下面对console.log格式 function 的意义进行扩展。尚未提及的格式化功能之一是组级别,日志将支持,但stdout不会。

console.log('Begin...')

console.group()
console.log('Line 2 (console.log)')
process.stdout.write('Line 3 (process.stdout)\n')
console.log('Line 4 (console.log)')
process.stdout.write('Line 5 (process.stdout)') // no newline
console.groupEnd()

console.log('...done')

Output:

Begin...
  Line 2 (console.log)
Line 3 (process.stdout)
  Line 4 (console.log)
Line 5 (process.stdout)...done

请注意, stdout不遵循 console.group 格式并始终写入行首,而console.log分组并适当缩进。


仅对日志语句(和一个附加组)执行相同的操作:

console.log('Begin...')

console.group()
console.log('Line 2 (console.log)')
console.log('Line 3 (console.log)')
console.log('Line 4 (console.log)')
console.log('Line 5 (console.log)')
console.group()
console.log('Line 6 (console.log)')
console.log('Line 7 (console.log)')
console.groupEnd()
console.groupEnd()

console.log('...done')

Output:

Begin...
  Line 2 (console.log)
  Line 3 (console.log)
  Line 4 (console.log)
  Line 5 (console.log)
    Line 6 (console.log)
    Line 7 (console.log)
...done

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM