背景:我有麦克风流进来,我想避免额外的复制操作,以节省整个系统MIPS.据我所知,对于音频流而言,即使在引擎盖下有记忆镜,也不会花费大量的MIPS,但我也计划在30fps和UHD分辨率下以相机帧流式传输.以30fps制作UHD分辨率像素数据的多个副本是非常低效的,因此需要一些关于此的建议.
示例代码:
var spawn = require('child_process').spawn var Passthrough = require('stream').Passthrough; var ps = null; //var audioStream = new Passthrough; //var infoStream = new Passthrough; var start = function() { if(ps == null) { ps = spawn('rec',['-b',16,'--endian','little','-c',1,'-r',16000,'-e','signed-integer','-t','raw','-']); //ps.stdout.pipe(audioStream); //ps.stderr.pipe(infoStream); exports.audioStream = ps.stdout; exports.infoStream = ps.stderr; } }; var stop = function() { if(ps) { ps.kill(); ps = null; } }; //exports.audioStream = audioStream; //exports.infoStream = infoStream; exports.startCapture = start; exports.stopCapture = stop;
以下是问题:
>为了能够执行流量控制,source.pipe(dest)是否会执行从源内存到目标内存的memcpy,或者它会将内存中的引用传递到目标吗?
>注释代码包含Passthrough类实例化 – 我目前假设Passthrough也会导致memcopies,所以我在整个系统中保存了一个memcpy操作,因为我在上面的注释中添加了?
>如果我必须在Process和Spawned Child进程之间创建一个管道(使用如How to transfer/stream big data from/to child processes in node.js without using the blocking stdio?所示的child_process.spawn()),我认为肯定会产生memcpy?反正有没有提到参考而不是复制?
>这种行为是否因操作系统而异?我认为它应该是OS不可知的,但无论如何要问这个.
在此先感谢您的帮助.它将有助于我的架构很多.
解决方法
https://github.com/nodejs/node/blob/master/src/stream_wrap.cc
https://github.com/nodejs/node/blob/master/src/stream_base.cc
https://github.com/libuv/libuv/blob/v1.x/src/unix/stream.c
https://github.com/libuv/libuv/blob/v1.x/src/win/stream.c
我试着写一个基于theese和其他文件的复杂/巨大的解释但是我得出结论,最好给你一个关于我的经验/阅读告诉我节点内部工作的总结:
管道只是简单地连接流使得它看起来好像.on(“data”,…)由.write(…)调用,而两者之间没有任何膨胀.
现在我们需要将js世界与c / c世界分开.
在处理js中的数据时,我们使用缓冲区. https://github.com/nodejs/node/blob/master/src/node_buffer.cc
它们只是代表分配的内存,顶部有一些糖果来操作它.
如果你将一个进程的stdout连接到一些.on(“data”,…)监听器,它会将传入的块复制到一个Buffer对象中,以便在js世界中进一步使用.
在js世界中,你有像.pause()等方法(你可以在节点中的steam api文档中看到),以防止进程占用内存,以防传入数据的流速超过其处理速度.
连接进程的stdout,例如通过管道传出tcp端口将导致类似于Nginx操作的连接.它将连接theese流,就像它们通过将传入数据直接复制到传出流而直接相互通信一样.
一旦暂停流,节点将使用内部缓冲,以防它无法暂停传入的流.
所以对于你的场景,你应该只是做测试.
尝试通过节点中的传入流接收数据,暂停流并查看发生的情况.
我不确定节点是否会使用内部缓冲,或者如果您尝试运行的进程将暂停,直到它可以继续发送数据.
我希望这个过程停止,直到你继续流.
为了传输巨大的图像,我建议将它们分块传输或直接传输到传出端口.
块方式允许您一次将数据发送到多个客户端,并将内存占用率保持在相当低的水平.
PS你应该看看我刚刚找到的这个要点:https://gist.github.com/joyrexus/10026630它深入解释了如何与流进行交互
版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。