C++:将成员函数作为普通函数指针传递的闭包

2024-03-12

我正在尝试调用外部库的成员函数,该函数接受函数指针作为参数:

Timer::every(unsigned long period, void (*callback)(void));

但不幸的是我想传递的参数是一个成员函数:

void MyClass::the_method_i_want_to_pass(void);

由于我正在 Arduino (AVR) 下为 ATMega 编程,因此对 c++11 的支持有限。我的第一种方法引发了类型错误:

void MyClass::the_method_i_want_to_pass() {...}

MyClass::MyClass() {
    // constructor

    Timer *timer = new Timer();
    timer->every(500, [this](){this->the_method_i_want_to_pass();})
}

编译器输出:

警告:警告:lambda 表达式仅适用于 -std=c++11 或 -std=gnu++11 [默认启用]

错误:没有匹配的函数可用于调用“Timer::every(int, MyClass::MyClass()::__lambda0)”

  1. 还有其他/更好的解决方案吗?
  2. 关于我当前的方法:(如何)当需要函数指针时是否可以传递对 lambda 的引用?
  3. 我如何查明 Arduino/AVR 是否支持这些 lambda(请参阅“警告”)?

你的基本问题是你的Timer图书馆写得不好:应该采取void(*)(void*), void*至少。

如果没有 pvoid 或等效项,则无法传递除执行代码中的地址之外的任何状态来运行过程。作为一种方法也重新布线this指针,你运气不好。

现在,如果你的实例MyClass是一个单例,你可以得到this从其他地方。

如果做不到这一点,您需要创建自己的全局状态,以便您可以从特定回调映射到某个状态。如果你的数量有限MyClass以及其他消费者Timer,您可以拥有一些固定函数,并让它们在全局范围内存储额外的状态。

这都是黑客行为。接下来的情况更糟。

编写一个具有某些全局状态的动态库,以及void()界面。添加回调时,复制该动态库,在运行时修改其全局状态,将其写为不同名称的库,加载它,并将纯回调函数传递给您的Timer class.

或者在没有库的情况下通过手动编写机器代码并将页面标记为可执行文件来执行等效操作。

这些都是糟糕的解决方案。这让我找到了一个好的办法:找到一个更好的Timer。如果他们搞砸了这么简单的事情,那么图书馆的其他部分也可能很糟糕。

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

C++:将成员函数作为普通函数指针传递的闭包 的相关文章

  • 编译时运算符

    有人可以列出 C 中可用的所有编译时运算符吗 C 中有两个运算符 无论操作数如何 它们的结果始终可以在编译时确定 它们是sizeof 1 and 2 当然 其他运算符的许多特殊用途可以在编译时解决 例如标准中列出的那些整数常量表达式 1 与
  • 没有强命名的代码签名是否会让您的应用程序容易被滥用?

    尝试了解authenticode代码签名和强命名 我是否正确地认为 如果我对引用一些 dll 非强命名 的 exe 进行代码签名 恶意用户就可以替换我的 DLL 并以看似由我签名但正在运行的方式分发应用程序他们的代码 假设这是真的 那么您似
  • 我如何才能等待多个事情

    我正在使用 C 11 和 stl 线程编写一个线程安全队列 WaitAndPop 方法当前如下所示 我希望能够将一些内容传递给 WaitAndPop 来指示调用线程是否已被要求停止 如果 WaitAndPop 等待并返回队列的元素 则应返回
  • WCF RIA 服务 - 加载多个实体

    我正在寻找一种模式来解决以下问题 我认为这很常见 我正在使用 WCF RIA 服务在初始加载时将多个实体返回给客户端 我希望两个实体异步加载 以免锁定 UI 并且我想利用 RIA 服务来执行此操作 我的解决方案如下 似乎有效 这种方法会遇到
  • GLKit的GLKMatrix“列专业”如何?

    前提A 当谈论线性存储器中的 列主 矩阵时 列被一个接一个地指定 使得存储器中的前 4 个条目对应于矩阵中的第一列 另一方面 行主 矩阵被理解为依次指定行 以便内存中的前 4 个条目指定矩阵的第一行 A GLKMatrix4看起来像这样 u
  • 在结构中使用 typedef 枚举并避免类型混合警告

    我正在使用 C99 我的编译器是 IAR Embedded workbench 但我认为这个问题对于其他一些编译器也有效 我有一个 typedef 枚举 其中包含一些项目 并且我向该新类型的结构添加了一个元素 typedef enum fo
  • 查找c中结构元素的偏移量

    struct a struct b int i float j x struct c int k float l y z 谁能解释一下如何找到偏移量int k这样我们就可以找到地址int i Use offsetof 找到从开始处的偏移量z
  • 从Web API同步调用外部api

    我需要从我的 Web API 2 控制器调用外部 api 类似于此处的要求 使用 HttpClient 从 Web API 操作调用外部 HTTP 服务 https stackoverflow com questions 13222998
  • BitTorrent 追踪器宣布问题

    我花了一点业余时间编写 BitTorrent 客户端 主要是出于好奇 但部分是出于提高我的 C 技能的愿望 我一直在使用理论维基 http wiki theory org BitTorrentSpecification作为我的向导 我已经建
  • 不同枚举类型的范围和可转换性

    在什么条件下可以从一种枚举类型转换为另一种枚举类型 让我们考虑以下代码 include
  • 堆栈溢出:堆栈空间中重复的临时分配?

    struct MemBlock char mem 1024 MemBlock operator const MemBlock b const return MemBlock global void foo int step 0 if ste
  • C# 中通过 Process.Kill() 终止的进程的退出代码

    如果在我的 C 应用程序中 我正在创建一个可以正常终止或开始行为异常的子进程 在这种情况下 我通过调用 Process Kill 来终止它 但是 我想知道该进程是否已退出通常情况下 我知道我可以获得终止进程的错误代码 但是正常的退出代码是什
  • C#中如何移动PictureBox?

    我已经使用此代码来移动图片框pictureBox MouseMove event pictureBox Location new System Drawing Point e Location 但是当我尝试执行时 图片框闪烁并且无法识别确切
  • 垃圾收集器是否在单独的进程中运行?

    垃圾收集器是否在单独的进程中启动 例如 如果我们尝试测量某段代码所花费的进程时间 并且在此期间垃圾收集器开始收集 它会在新进程上启动还是在同一进程中启动 它的工作原理如下吗 Code Process 1 gt Garbage Collect
  • Windows 窗体:如果文本太长,请添加新行到标签

    我正在使用 C 有时 从网络服务返回的文本 我在标签中显示 太长 并且会在表单边缘被截断 如果标签不适合表单 是否有一种简单的方法可以在标签中添加换行符 Thanks 如果您将标签设置为autosize 它会随着您输入的任何文本自动增长 为
  • cmake 将标头包含到每个源文件中

    其实我有一个简单的问题 但找不到答案 也许你可以给我指一个副本 所以 问题是 是否可以告诉 cmake 指示编译器在每个源文件的开头自动包含一些头文件 这样就不需要放置 include foo h 了 谢谢 CMake 没有针对此特定用例的
  • IEnumreable 动态和 lambda

    我想在 a 上使用 lambda 表达式IEnumerable
  • C# - OutOfMemoryException 在 JSON 文件上保存列表

    我正在尝试保存压力图的流数据 基本上我有一个压力矩阵定义为 double pressureMatrix new double e Data GetLength 0 e Data GetLength 1 基本上 我得到了其中之一pressur
  • C++ 标准是否指定了编译器的 STL 实现细节?

    在写答案时this https stackoverflow com questions 30909296 can you put a pimpl class inside a vector我遇到了一个有趣的情况 这个问题演示了这样一种情况
  • 对来自流读取器的过滤数据执行小计

    编辑问题未得到解答 我有一个基于 1 个标准的过滤输出 前 3 个数字是 110 210 或 310 给出 3 个不同的组 从流阅读器控制台 问题已编辑 因为第一个答案是我给出的具体示例的字面解决方案 我使用的实际字符串长度为 450 个

随机推荐

  • 在 Android 谷歌地图 v2 上保存标记

    我正在使用 Android Google 地图 v2 API 并将其设置为在长按时添加标记 我需要一种方法来保存这些标记并在应用程序再次恢复时重新加载它们 做到这一点的最佳方法是什么 请帮忙 目前我添加标记如下 map addMarker
  • 在shared_ptr的自定义删除器中检查nullptr是否有意义?

    我见过一些使用的代码std shared ptr使用自定义删除器来测试 nullptr 的参数 例如 MyClass其中有一个close 方法并用一些构造CreateMyClass auto pMyClass std shared ptr
  • 如何用背景颜色填充整个div

    我试图获取背景颜色来填充 bootstrap 中子 div 中的整个 div 但我完全陷入困境 我希望右侧部分为黄色 但它仅突出显示 div 中的文本 这是一个fiddle https jsfiddle net hcgriggs yjcrc
  • 如何在不创建 new Form() 的情况下从 Form2 访问 Form1 函数;

    我是 C 新手 正如我现在面临的问题 public void snz btn Click object sender EventArgs e this Close beside than this Form1 fs new Form1 fs
  • 如何在Python中生成唯一ID? [复制]

    这个问题在这里已经有答案了 我需要根据随机值生成一个唯一的 ID Perhaps uuid uuid4 可能会完成这项工作 看uuid http docs python org library uuid html了解更多信息
  • 如何将来自其他分叉的未合并的上游拉取请求应用到我的分叉中?

    我在 GitHub 上有一个分叉的项目有一个新的拉取请求 我想将其拉入我的分叉中 但作者尚未拉入 有没有一种简单的方法可以将其他分叉的拉取请求应用到我的分叉中 我还缺少其他东西吗 更新 通过网页 您还可以通过 github 网页执行此操作
  • Python Pandas:根据时间范围删除时间序列的行

    我有以下时间序列 start pd to datetime 2016 1 1 end pd to datetime 2016 1 15 rng pd date range start end freq 2h df pd DataFrame
  • 单一职责和混合

    鉴于Mixins http en wikipedia org wiki Mixin通常会在类中引入新的行为 这通常意味着一个类将具有多个行为 如果一个类具有单一职责 则这被定义为该类只有一个变更原因 所以 我可以从两个不同的角度来看待这个问
  • ASP.NET Core 3.1 MVC 中的本地化

    我正在尝试将本地化添加到我的 ASP NET Core 3 1 MVC 项目中 遗憾的是我找不到任何文章或教程来展示如何以简单的方式完成此操作 每个人都有一些我无法理解的问题 谁能告诉我一个简单的方法来做到这一点 好的 我尝试执行syncf
  • document.referrer 是否等于 HTTP Referer 标头?

    如果我点击正常链接http google com http google com to http example com http example com 通常我的浏览器发送到 example com 的 httpreferrer 标头是
  • Android 应用程序的 Twitter 登录

    谁能告诉我从我的 Android 应用程序执行 Twitter 登录开放身份验证的正确步骤 还有一件事是可以在没有 gng 的情况下从我的应用程序执行 Twitter 帐户的登录身份验证到 Twitter 登录页面吗 想法是使用 Twitt
  • Spring data jpa中save和saveAndFlush的区别

    我正在尝试通过测试一些 CRUD 操作来学习 spring data JPAJpaRepository 我遇到了两种方法save and saveAndFlush 我不明白这两者之间的区别 通话时save我的更改也被保存到数据库中 所以有什
  • 如何在更新单独结构中的 @AppStorage 后更新 SwiftUI 视图

    我有以下课程 struct PriceFormatter AppStorage UserDefaultsKey savedCurrency var savedCurrency String let price Float init pric
  • 创建动态规则

    我正在尝试使用代码动态调整相对布局中的图像大小 int height v getHeight int width v getWidth height 50 width 50 RelativeLayout LayoutParams layou
  • NestJs:无法读取模块文件中的环境变量,但可以读取服务文件中的环境变量?

    我有一个 env文件位于我的 NestJs 项目的根目录中 其中包含一些环境变量 奇怪的是 我能够读取服务文件中的变量 但不能读取模块文件中的变量 所以在像这样的服务文件中users service ts 这有效 saveAvatar co
  • 无法从 CursorWindow 读取第 0 行、第 -1 列

    我正在尝试获取表中的记录 我正在使用这个代码 if c null if c moveToFirst String tipId c getString c getColumnIndex DAO TIP ID toString trim Sys
  • 如何为 Prometheus 检测 Java 应用程序代码指标

    我正在尝试将 Java 应用程序的自定义值指标导出到 Prometheus 我读到可以使用 Push Gateway 来完成 下面是我使用下一个方法的示例 static void executeBatchJob throws Excepti
  • pecl 找不到 imagick 包

    我正在尝试在我的 Mac 上安装 imagick 我搜索并阅读了很多 包括这个 但是 我在最后一步遇到了问题 即通过 pecl 实际安装 imagick 软件包 我收到此错误 No releases available for packag
  • 如何为 pwa 添加自定义安装按钮

    我想添加自定义install网站内我的渐进式网络应用程序的按钮 我红色了很多文章并尝试了他们提供的答案 他们使用beforeinstallprompt let deferredPrompt window addEventListener b
  • C++:将成员函数作为普通函数指针传递的闭包

    我正在尝试调用外部库的成员函数 该函数接受函数指针作为参数 Timer every unsigned long period void callback void 但不幸的是我想传递的参数是一个成员函数 void MyClass the m