gpt4 book ai didi

c++ - 设计用于标记和传输树的 C++ DSL

转载 作者:塔克拉玛干 更新时间:2023-11-03 02:22:04 25 4
gpt4 key购买 nike

简而言之

我正在尝试为 C 库设计一个更好的 C++ 接口(interface),它通过通信 channel 发送树状表达式(à la iostreams vs stdio)。我不确定是否有可能在 C++ 中设计一个 DSL 来标记这些树同时避免运行时开销,如果是的话,如何。

C库的简单解释

有一个 C 库可以通过通信 channel 发送“表达式”。这里的“表达式”是指树结构,可以用类似于函数调用的方式方便地表示。

例如,

f(1, 2, g(3), "foo")

表示这棵树:

Mathematica graphics

你们中的一些人可能认识 Mathematica在这一点上,但我决定将其排除在外,因为它与问题无关。

我们将 f 称为 head12g(3) 作为参数

要发送此表达式,我们将编写以下内容:

putHead("f" /* name */, 3 /* argument count */);
putInteger(1);
putInteger(2);
putHead("g" /* name */, 1 /* argument count */);
putInteger(3);
putString("foo");

问题

是否可以为此设计一个具有以下特点的更方便的C++ API?

  1. 编写起来更简洁(想想 iostreams vs stdio)
  2. 无需为每个头显式指定参数计数;取而代之的是使用一种方便的表示法(类似于上面的 f(1,2,g(3))),它从中自动推断参数计数
  3. 在没有运行时开销的情况下实现 (2)(即在编译时推断参数计数)
  4. 必须在后台使用上述 C 接口(interface)

我可以使用类似流的接口(interface)来执行 (1)(即无需明确指定每个参数的 Integer、String 等类型)。我可以以涉及额外运行时计算的方式执行 (2)。但我不知道考虑到 C++ 的特性,(2)/(3) together 是否可能。最后,我希望在 C++ 本身中为这些表达式提供一个方便的符号。

那么是否有可能在 C++ 中为此设计一个 DSL,同时避免所有运行时开销?如果是,如何?我不一定要寻找以代码为答案的完整解决方案,只是寻找一些入门指南或可能有效的方法摘要。

最佳答案

我可以想出几种在 C++ 中表示树的方法。其中一些(#1、#2)的实现将涉及构建一个中间结构,然后在最后调用 C 函数。其他人(#5、#6)可以随时调用 C 函数,因为在编译时已知任何节点的子节点数。

1) 使用流畅的接口(interface)和重载:

Tree()
.head("f")
.put(1)
.put(2)
.head("g")
.put(3)
.end()
.put("foo")
.end();

2) 或者,不调用 end():

head("f")
.put(1)
.put(2)
.put(head("g")
.put(3))
.put("foo");

3) 使用运算符<<:

Tree("f")
<< 1
<< 2
<< (Tree("g") << 3)
<< "foo";

4) 使用运算符():

Tree("f")
(1)
(2)
(Tree("g")(3))
("foo")

5) 使用 std::initializer_list,其中 Node 是一种可从 int 和 std::string 隐式转换的类型:

Tree { "f", {
1,
2,
{ "g", { 3 } }
"foo",
} }

6) 使用可变参数模板:

head("f").put(
1,
2,
head("g").put(3)
"foo");

关于c++ - 设计用于标记和传输树的 C++ DSL,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/35970776/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com