Python 中非常简单的 C++ 代码生成






4.81/5 (16投票s)
快速生成重复的 C++、C# 或 Java 代码,从 Python 可以读取的任何数据中生成。
引言
你对学习曲线过敏,并且想立即生成代码!这里有一个易于定制的 100 行 Python 模块,仅比 f.writeline
高一个等级。
使用代码
让我们从一个非常简单的例子开始(不要指出 main
返回 int
,好吗!这只是一个例子)。
from CodeGen import *
cpp = CppFile("test.cpp")
cpp("#include <iostream>")
with cpp.block("void main()"):
for i in range(5):
cpp('std::cout << "' + str(i) + '" << std::endl;')
cpp.close()
输出
#include <iostream>
void main()
{
std::cout << "0" << std::endl;
std::cout << "1" << std::endl;
std::cout << "2" << std::endl;
std::cout << "3" << std::endl;
std::cout << "4" << std::endl;
}
利用 Python 的 with
关键字,我们可以将语句封装在 {}
块中,这些块会自动关闭,并具有正确的缩进,以便输出保持可读。
替换
在生成更复杂的代码时,你很快就会意识到你的 Python 脚本变得越来越难以阅读,到处都是丑陋的字符串连接。 这时 subs
方法就派上用场了
from CodeGen import *
cpp = CppFile("test.cpp")
cpp("#include <iostream>")
with cpp.block("void main()"):
for i in range(5):
with cpp.subs(i=str(i), xi="x"+str(i+1)):
cpp('int $xi$ = $i$;')
cpp.close()
这会在客户端生成
#include <iostream>
void main()
{
int x1 = 0;
int x2 = 1;
int x3 = 2;
int x4 = 3;
int x5 = 4;
}
这些替换在 Python with
块内有效,并且可以嵌套。
差不多就是这样了
为了完成,这里有一个更复杂的例子,用于生成以下代码
class ClassX
{
protected:
A a;
B b;
C c;
public:
ClassX(A a, B b, C c)
{
this->a = a;
this->b = b;
this->c = c;
}
A getA()
{
return this->a;
}
B getB()
{
return this->b;
}
C getC()
{
return this->c;
}
};
class ClassY
{
protected:
P p;
Q q;
public:
ClassY(P p, Q q)
{
this->p = p;
this->q = q;
}
P getP()
{
return this->p;
}
Q getQ()
{
return this->q;
}
};
请查看 CodeGen.py
,了解 label
函数的实现方式,以了解如何通过语言特定功能扩展代码。
from CodeGen import *
cpp = CppFile("test.cpp")
CLASS_NAMES = ["ClassX", "ClassY"]
VAR_NAMES = { "ClassX": ["A", "B", "C"],
"ClassY": ["P","Q"] }
for className in CLASS_NAMES:
with cpp.subs(ClassName=className):
with cpp.block("class $ClassName$", ";"):
cpp.label("protected")
for varName in VAR_NAMES[className]:
with cpp.subs(A=varName, a=varName.lower()):
cpp("$A$ $a$;")
cpp.label("public")
with cpp.subs(**{"A a": ", ".join([x + " " + x.lower() for x in VAR_NAMES[className]])}):
with cpp.block("$ClassName$($A a$)"):
for varName in VAR_NAMES[className]:
with cpp.subs(a=varName.lower()):
cpp("this->$a$ = $a$;")
for varName in VAR_NAMES[className]:
with cpp.subs(A=varName, a=varName.lower(), getA="get"+varName):
with cpp.block("$A$ $getA$()"):
cpp("return this->$a$;")
cpp.close()