50

我有一个 C++ 源文件和一个 Python 源文件。我希望 C++ 源文件能够将 Python 源文件的内容用作大字符串文字。我可以做这样的事情:

char* python_code = "
#include "script.py"
"

但这行不通,因为每行的末尾都需要有 \'s。我可以手动复制和粘贴 Python 代码的内容,并用引号和终止的 \n 将每一行括起来,但这很难看。即使 python 源代码将有效地编译到我的 C++ 应用程序中,我还是想将它保存在一个单独的文件中,因为它更有条理并且与编辑器一起工作更好(emacs 不够聪明,无法识别C字符串文字是 python 代码,当你在里面时切换到 python 模式)。

请不要建议我使用 PyRun_File,这是我首先要避免的;)

4

7 回答 7

42

C/C++ 预处理器以标记为单位进行操作,字符串文字是单个标记。因此,您不能在这样的字符串文字中间进行干预。

您可以将 script.py 预处理为:

"some code\n"
"some more code that will be appended\n"

然而,#include 。或者您可以使用它来生成一个准备好包含的 C 静态数组。xxd​ -i

于 2009-08-07T18:28:41.547 回答
13

这不会让你一直到那里,但它会让你非常接近。

假设script.py包含这个:

print "The current CPU time in seconds is: ", time.clock()

首先,像这样包装它:

STRINGIFY(print "The current CPU time in seconds is: ", time.clock())

然后,就在您包含它之前,请执行以下操作:

#define STRINGIFY(x) #x

const char * script_py =
#include "script.py"
;

可能有比这更严格的答案,但我仍在寻找。

于 2013-03-06T02:34:42.660 回答
4

如果您的环境/工具集具有该功能,则执行此类操作的最佳方法是将文件作为资源包含在内。

如果不是(如嵌入式系统等),您可以使用 bin2c 实用程序(类似于http://stud3.tuwien.ac.at/~e0025274/bin2c/bin2c.c)。它将采用文件的二进制表示并输出一个 C 源文件,其中包含一个初始化为该数据的字节数组。如果您希望数组被“\0”终止,您可能需要对工具或输出文件进行一些调整。

将运行 bin2c 实用程序合并到您的 makefile 中(或作为您用于驱动构建的任何内容的预构建步骤)。然后只需将文件编译并与您的应用程序链接,您的字符串(或文件的任何其他图像)就位于由数组表示的一块内存中。

如果您将文本文件作为字符串包含在内,您应该注意的一件事是行尾可能与函数期望的不匹配 - 这可能是您想要添加到 bin2c 实用程序或者您想要的另一件事确保您的代码正确处理文件中的任何行结尾。也许修改 bin2c 实用程序以具有“-s”开关,指示您希望将文本文件合并为字符串,以便行尾将被规范化,并且零字节将位于数组的末尾。

于 2009-08-07T23:16:26.287 回答
1

您将不得不对 Python 代码进行一些自己的处理,以处理其中出现的任何双引号、反斜杠、三元组以及可能的其他内容。您可以同时将换行符转换为 \n (或反斜杠转义它们)并在两端添加双引号。结果将是从 Python 源文件生成的头文件,然后您可以#include。使用您的构建过程自动执行此操作,以便您仍然可以将 Python 源代码编辑为 Python。

于 2009-08-07T18:32:57.623 回答
1

您可以使用Cog作为构建过程的一部分(进行预处理和嵌入代码)。我承认这样做的结果可能并不理想,因为你最终会在两个地方看到代码。但每当我看到“Python”、“C++”和“预处理器”接近时,我觉得它值得一提。

于 2009-08-07T18:58:11.627 回答
-2

这是使用 cmd.exe 自动转换的方法

------ html2h.bat ------

@echo off
echo const char * html_page = "\
sed "/.*/ s/$/ \\n\\/" ../src/page.html | sed s/\"/\\\x22/g 
echo.
echo ";

它被称为

cmd /c "..\Debug\html2h.bat" > "..\debug\src\html.h"

并附在代码上

#include "../Debug/src/html.h"
printf("%s\n", html_page);

这是非常依赖系统的方法,但是,作为大多数人,我不喜欢十六进制转储。

于 2013-05-07T16:24:06.407 回答
-10

使用fopengetlinefclose

于 2009-08-07T19:42:04.957 回答