gpt4 book ai didi

c++ - 在运行时从 RPN 构造函数可调用对象

转载 作者:行者123 更新时间:2023-11-28 06:10:32 24 4
gpt4 key购买 nike

我正在设计一个程序来对流式数据执行某些操作。操作由运行时提供的 RPN(逆向抛光表示法)表达式定义。数据从文件源流式传输,一次一个固定大小的部分。操作引用一些当前输入的数据部分,例如 data[1]。该程序对所有输入部分应用相同的操作(并流出结果)。

实现对数字和算术运算给出结果的 RPN 解析器非常容易。然而,使用这样的实现意味着为每个数据部分重新解析 RPN。

我想要实现的是以某种方式构建一个对象,该对象将根据数据的基本操作字母表保存曾经解析过的 RPN 实现,程序将在其中提供输入数据(或填写输入),调用对象的operator()获取并输出结果。

如何使用“非现代”C++(无 C++11C++14)?

最佳答案

自其 RPN 以来,操作可以建模为堆栈的一系列转换。将一个输入部分加载到堆栈上,然后按顺序执行您的操作就可以解决问题。不需要树,它隐含在操作顺序中。也不需要重新解析,它确实是一系列操作(函数或仿函数),而不是一系列表示操作的符号。

我会选择仿函数,因为我更喜欢存储对象的引用或指针,而不是存储函数的引用或指针。您将其实现为一个具有重载运算符 () 的类,该运算符执行所需的堆栈转换(例如,如果它是乘法仿函数,则将两个顶部元素相乘)。

Ancient device working that way...

上图:古代设备以这种方式工作......

关于堆栈中存储的内容和不存储的内容:

  • 首先,您的操作数存储在与输入顺序匹配的队列中
  • 您的运算符对象(解析一次且永不更改的结果)单独存储在运算符队列中。
  • 应用'get'运算符将一个操作数从队列转移到操作数栈

例如如果你想计算

sin (3 + 4) / (5 + 6)

你的操作数队列是:

[start] 3 4 5 6 [end]

你的运算符对象队列(它包含指向仿函数的指针,而不是符号,每个仿函数只有一个实例,但可能被多次引用)是:

[start] &getFunctor &getFunctor &addFunctor &sinFunctor &getFunctor &getFunctor &addFunctor &divideFunctor [begin]

你的操作数栈开始时是空的:

[top][bottom]

应用运算符(operator)队列将随后为您提供:

(get)    [top] 3 [bottom]
(get) [top] 3 4 [bottom]
(add) [top] 7 [bottom]
(sin) [top] 0.657 [bottom]
(get) [top] 5 0.657 [bottom]
(get) [top] 5 6 0.657 [bottom]
(add) [top] 11 0.657[bottom]
(divide) [top] 0.0597 [bottom]

如果您随后想要对例如应用完全相同的操作

[start]10 20 30 40[end]

只需替换操作数队列(或者让操作数队列的起始指针指向操作数文件的下一个“ block ”,然后针对这个新的操作数序列再次运行运算符(operator)队列。

请注意,如上所述,运算符队列不包含运算符符号,而是指向准备就绪的函数对象的指针,这些函数对象将在您调用它们时立即执行它们的操作,而无需重新解析或重新生成代码。

因此,如果您有大量数据:

[start of file]3 4 5 6   10 20 30 40   -1 -10 15 80 ...[end of file]

您只需继续应用相同的运算符(operator)队列,一切都会正常进行。

关于c++ - 在运行时从 RPN 构造函数可调用对象,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/31361519/

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