首页 > 解决方案 > 我可以从内存中运行 Windows 批处理脚本吗?

问题描述

假设我在我的程序中动态生成这样的脚本并将其保存在 C++ 字符串变量中。我该如何运行它?我是否必须先将其保存到文件中,然后指示 cmd.exe 运行它?

我知道您可以像这样将命令通过管道传输到 cmd.exe:

type script.bat | cmd

但这样做的效果不是运行 script.bat 。相反,Windows 会启动一个新的 cmd.exe 实例,打印徽标并等待命令在执行之前回显到屏幕上。例如,尝试

echo echo hello | cmd

因此,script.bat 中的每一行都作为一个独立的命令处理,就像您在命令行中输入它一样(这就是 cmd.exe 认为您正在做的事情!)。那不好。你不能像那样运行一般脚本。您可能有跨越多行的循环和分支。那么我能做什么呢?

我知道您可以将多个命令放在一行中,如下所示:

cmd /C "echo hello & echo world"

但是每个批处理脚本都可以以某种方式轻松地更改为 oneliner 吗?如果脚本是:

@echo off

echo hello
echo world

我可以用上面的 onlineer 替换它,但是如果它包含一个跨越几行带括号的 for 循环?

所以标题问题可以重新表述为:每个批处理脚本都可以转换为单行吗?如果是,那怎么办?如果没有,有什么好的解决方案吗?我可以以某种方式欺骗 cmd.exe 认为它从文件中读取批处理脚本,而实际上它是从我的程序中获取的吗?

编辑:一个有趣的怪癖是:

echo echo hello | cmd /C "for /f "tokens=*" %a in ('more') do @%a"

但同样,每一行都被解释为一个独立的命令。

标签: windowsbatch-filecmd

解决方案


FILE_ATTRIBUTE_TEMPORARY文件被用于临时存储。文件系统试图将所有数据保存在内存中以便更快地访问,而不是将数据刷新回大容量存储。一旦不再需要临时文件,应用程序应立即将其删除。

FILE_FLAG_DELETE_ON_CLOSE表示操作系统将在文件的所有句柄关闭后立即删除文件,而不仅仅是您为其指定 FILE_FLAG_DELETE_ON_CLOSE 的句柄。除非使用 FILE_SHARE_DELETE,否则对该文件的后续打开请求将失败。

https://docs.microsoft.com/en-us/windows/win32/api/fileapi/nf-fileapi-createfilea

如果您使用这些标志指定临时文件,则可以将其作为批处理运行。除非您承受内存压力,否则该文件将永远不会在硬盘上。

PS:如果您在“打开文件”对话框中键入 URL,记事本将打开 Web 文件。记事本是潜在系统功能的测试平台。

PPS:你可以管它。cmd /c < ..\win.ini(并不是说这有意义,但我们在 Windows 中不再有标准的批处理文件)。


推荐阅读