c++ std::function 比 c function 慢

来聊一聊std::function和lambda性能效率问题 详细讲解std::function和lambda在日常开发过程,大家最关心的性能效率问题 阅读详情

项目中大量使用functional来替代virtual函数,那么functor函数相对于c function带来的额外成本是多少呢?今天构造一个测试用例来测试下。g++ (GCC) 4.8.5 20150623 (Red Hat 4.8.5-28)

测试如下几种情况:

1.c function

int _func(int a, int b) {
  return a + b;
}

2.重载operator()的struct

struct _struct {
  int operator()(int a, int b) {
     return a + b;
  }
};

3.类方法

class _Class{
public:
   int op(int a, int b) {return a + b;} 
};

4.结构体嵌套类指针

struct _struct2 {
  _Class *p; 
  int operator()(int a, int b) {
     return p->op(a, b); 
  }
};

对如上几种方式分别调用100000次。分别在O0 O1 O3 测试结果如下

 time(O0)time(O1)time(O3)
纯函数3227846
结构体3457735
类3637233
类bind17925658433
functional2506548288
结构体嵌套类7139136

结论

我们可以得出一个结论,g++不提供优化参数时, std::bind返回的function性能堪忧,到O3也和纯c相差甚远。同时,类方法的结果也印证了c++内存模型所讲的类方法(非virtual)只是改了名字的c方法。

c++中的functional为什么性能和c function相差这么远?这个结果与常规的认知(结构体内包含类指针)不一致,采用类型擦除手段会带来这么大的负担? 看结果通过结构体保存类指针的方式比较稳定。

 

测试代码如下

#include <iostream>
#include <functional>
#include <sys/time.h>


int _func(int a, int b) {
  return a + b;
}

struct _struct {
  int operator()(int a, int b) {
     return a + b;
  }
};

class _Class{
public:
   int op(int a, int b) {return a + b;}
};

struct _struct2 {
  _Class *p;
  int operator()(int a, int b) {
     return p->op(a, b);
  }
};


// 纯函数
void test_func() {
  printf("测试纯函数\n");
  int i = 0;
  int s = 0;
  while(i++ < 100000) {
    s+=_func(3, 4);
  }
}

// 测试结构体实现的functor
void test_struct() {
  printf("测试结构体\n");
  int i = 0;
  int s = 0;
  struct _struct f;
  while(i++ < 100000) {
    s+=f(3, 4);
  }
}

// 通过类调用的结构体
void test_struct2() {
  printf("测试结构体嵌套类\n");
  int i = 0;
  int s = 0;
  struct _struct2 f;
  _Class t;
  f.p = &t;
  while(i++ < 100000) {
    s+=f(3, 4);
  }
}


// 测试类
void test_class() {
  printf("测试结类\n");
  int i = 0;
  int s = 0;
  _Class t;
  while(i++ < 100000) {
    s+=t.op(3, 4);
  }
}


// 测试bind class
void test_class_functor() {
  printf("测试类bind\n");
  int i = 0;
  int s = 0;
  _Class t;
  std::function<int(int, int)> functor = std::bind(&_Class::op, &t, std::placeholders::_1, std::placeholders::_2);
  while(i++ < 100000) {
    s+=functor(3, 4);
  }
}


// 测试function
void test_functor() {
  printf("测试function\n");
  int i = 0;
  int s = 0;
  std::function<int(int, int)> functor2 = [](int a, int b) -> int {return a + b;};
  while(i++ < 100000) {
    s+=functor2(3, 4);
  }
}

int main(int argc, const char **argv)
{
  struct timeval tv;
  gettimeofday(&tv, NULL);
  if (argv[1][0] == 'a') test_func(); 
  if (argv[1][0] == 'b') test_struct(); 
  if (argv[1][0] == 'c') test_struct2(); 
  if (argv[1][0] == 'd') test_class(); 
  if (argv[1][0] == 'e') test_class_functor(); 
  if (argv[1][0] == 'f') test_functor(); 
  struct timeval tv2;
  gettimeofday(&tv2, NULL);
  int d = (tv2.tv_sec * 1000000 + tv2.tv_usec) - (tv.tv_sec * 1000000 + tv.tv_usec);
  printf("%d \n", d);
}

 

C++11 新特性 ④ | 模板类 std::function 和标准库函数 std::bind 详细讲解模板类std::function和标准库函数std::bind。 阅读详情

相关推荐

Oracle恢复学习实战小结

     学习oracle10g 043课程有段时间了,前一两个星期学习了backup/restore相关的内容,刚好公司有要求要为host服务器做一个备用机以防止数据意外丢失。于是,实战开始了。     首先介绍host服务器架构。host以oracle数据库作为底层数据存储,以公司总部开发的Santorin作为应用,主要提供给测试台架数据存储、数据访问、数据导入导出、用户权限管理和数据自动备份

kseawolfk的专栏 1034

std::function 的性能陷进

前言 std::function 的作用很强大,他让vector等保存不同类型函数的对象: function, functor, lambda…成为了可能。但他有一个潜在的性能风险:在保存lambda/bind时,如果对象的大小 大于两个指针的大小,他就需要分配动态空间。这是大部分人写C++的人不期望看到的。 function什么分配内存 先看function实现的几段代码:6.1.0a-2/in...

weixin_43530460的博客 2916

【车辆仿真】从0开始建立dSPACE RT Simulink工程:CAN通信(RTICANMM方法)

【工程环境信息】:本文基于链接文章搭建SCALEXIO Rack RTPC总线节点,用于与AutoBox通信硬件:上位机:惠普台式PC(Windows 11专业版)下位机(实时机):AutoBox (DS1006)板卡:DS6342软件:本文所使用的DBC链接提示:以下是本篇文章正文内容,下面案例可供参考!!!的部分一定记得配置,其他的按需配置RTICANMM的灵活度非常高,尽可能参考Help文档,理解相应的配置内容官方有RTICANMM的样例工程,在下方路径。

winnizap的博客 2381

性能特性测试系列2——c++11 std::function和正常调用函数效率比较

序 测试结果 测试数据解释 测试结果总结 总结与分析 原本是没打算写一个系列的,结果到了第二篇才开始写一个前言,本来不确定自己会测试哪些东西,哪些内容,以及有没有时间持续写这些比较偏的内容,但既然有打算写第二篇了,那么就写一个系列吧。本系列主要是QT和c++一些对比,当然也可能会有本篇这种纯c++的测试,看情况吧只能说。测到哪里写到哪里,时间就不太好说了= =。序 对于std::function和s

破晓前的彷徨 6199

AltiumDesigner相同模块复用操作

AltiumDesigner相同模块复用操作框选已布局好的A电路,作为复用模块创建Room同样的操作,框选C电路,然后也创建Room查看A电路的Chanel Offset显示设置复制Channel Offset查看B电路的Channel Offset复制A电路的Channel Offset到C电路Room格式的复制 框选已布局好的A电路,作为复用模块 创建Room 同样的操作,框选C电路,然后也创建Room 查看A电路的Chanel Offset 框选A模块的,然后点右下角的菜单——PCB——PCB

weixin_41947101的博客 5959

SAP ALV表格F4搜索帮助不触发DATA_CHANGE?3步排查搞定

本文针对SAP ALV表格中F4搜索帮助选择值后,DATA_CHANGE事件不触发的经典问题,提供了三步系统性排查方法。核心在于理解F4值回写机制,并需在事件处理中手动填充修改表以通知ALV控件数据变更,从而确保后续校验、自动计算等依赖DATA_CHANGE的逻辑能正常执行。

c2d3e4f的博客 1132

C++11中万能的可调用类型声明std::function

在C++11中,callable object 包括传统C函数,C++成员函数,函数对象(实现了()运算符的类的实例),lambda表达式(特殊函数对象)共4种。程序设计,特别是程序库设计时,经常需要涉及到回调,如果针对每种不同的callable object单独进行声明类型,代码将会非常散乱,也不灵活。如下示例: #include <iostream> #include <f...

大隐隐于野 1835

NE555构成多谐振荡器及三角波、正弦波的生成(附工程文件)

NE555构成多谐振荡器及三角波、正弦波的生成 续上一篇:NE555基本原理及相关公式的推导

qq_49979053的博客 5万+

C++11新特性之std::function

类模版std::function是一种通用、多态的函数封装。std::function的实例可以对任何可以调用的目标实体进行存储、复制、和调用操作,这些目标实体包括普通函数、Lambda表达式、函数指针、以及其它函数对象等。std::function对象是对C++中现有的可调用实体的一种类型安全的包裹(我们知道像函数指针这类可调用实体,是类型不安全的)。 通常std::function是一个函数...

大隐隐于野 474

AI赋能运筹优化:从参数生成到智能求解的工程实践

运筹学通过线性规划、整数规划等数学模型,为供应链、物流、生产排程等复杂决策问题寻找最优解,其核心价值在于提升资源利用效率与决策科学性。传统方法依赖精确的输入参数与专家经验,面临数据不准、建模门槛高、求解调优难等挑战。人工智能技术的引入,正从原理层面重塑这一流程:通过深度学习模型生成更贴合现实的动态参数(如需求分布、行驶时间),利用自然语言处理降低建模门槛,并借助强化学习对求解器进行智能参数调优。这种AI与运筹学的融合,在工程实践中显著提升了优化系统的自适应能力与求解效率,使其在应对实时交通、柔性生产调度等动

weixin_26913055的博客 595

腾讯文档API逆向分析:不用Selenium也能批量导出的黑科技

本文揭秘了如何通过Python逆向分析腾讯文档的隐藏API,实现无需Selenium即可批量导出在线表格的高效方法。详细解析了API调用流程、Cookie维护及异常处理技巧,相比传统方案性能提升显著,适用于大量文档导出的自动化场景。

h9j8k7l6m5n的博客 1201

C++11 std::function 基础用法

std::function是C++11标准库中提供的一种可调用对象的通用类型,它可以存储任意可调用对象,如函数指针,函数对象,成员函数指针和lambda表达式。std::function类模板是一个类似于函数指针的类型,但它是可以处理任意可调用对象的,并且可以检查调用对象是否为空。

Bobowen的博客 1万+

AIGC算法工程师-面试八股文-2025年版本-算法八股文/工程八股文/开放式问题

​两年前整理了《AIGC算法工程师 面试八股文》,全网一共有100w读者看过,收到了很多小伙伴的催更。Diffusion的技术发展非常快,博主特意整理了最近两年最新的八股文,内容非常全面,涵盖算法八股文/工程八股文/开放式问题三个大类,希望能为求职的读者们带来帮助。

沉迷单车的追风少年 4181

C++11:std::function<void()> func;

转自:使用std::function作为函数入参 关于std::function() 在C语言的时代,我们可以使用函数指针来吧一个函数作为参数传递,这样我们就可以实现回调函数的机制。到了C++11以后在标准库里引入了std::function模板类,这个模板概括了函数指针的概念 函数指针只能指向一个函数,而std::function对象可以代表任何可以调用的对象,比如说任何可以被当作函数一样调用的对象。 当你创建一个函数指针的时候,你必须定义这个函数签名(表征这个函数的入参,返回值等信息);同样的,当你创建

苦逼的程序猿☺ 1万+

老版QQ原生表情gif动态

这是老版的QQ表情,不过全是动态的的,Windows照片查看器是不会动的,可以右击用浏览器打开查看,再说一遍是老版的,只是分享给宁愿用老版也要动态的人。

假人有限元模型

假人模型,车辆碰撞假人有限元模型,适合做乘员安全的研究者利用

C++的std::function

std::function介绍,包括使用方法以及与函数指针的对比。

[PE]经典八炮的博客 3107

精雕软件(JDpaint) 5.5 绿色版

精雕软件(JDpaint) 5.5 绿色版精雕软件(JDpaint) 5.5 绿色版精雕软件(JDpaint) 5.5 绿色版

std::function与std::bind的使用总结

文章转载自: C++中函数指针的用途非常广泛,例如回调函数,接口类的设计等,但函数指针始终不太灵活,它只能指向全局或静态函数,对于类成员函数、lambda表达式或其他可调用对象就无能为力了,因此,C++11推出了std::function与std::bind这两件大杀器。 std::function vs 函数指针 C++函数指针相信大家用的很多了,用法最广泛的应该就是先定义函数指针的类型,然后在声明一个函数指针的变量作为另一个函数的入参,以此作为回调函数,如下列代码所示: typedef voi

zhc的博客 3830

TMS_WebGMaps_1.9.8.0_Full_Source

TMS_WebGMaps_1.9.8.0_Full_Source 全源码 delphi cbuilder

C++ std::function的开销

经常看到说function的开销比较大,慎用function之类的讨论。

qq_29426201的博客 1101

std::function

原文:https://blog.youkuaiyun.com/smstong/article/details/44958833 在C++11中,callable object 包括传统C函数,C++成员函数,函数对象(实现了()运算符的类的实例),lambda表达式(特殊函数对象)共4种。程序设计,特别是程序库设计时,经常需要涉及到回调,如果针对每种不同的callable object单独进行声明类型,代码将...

beizhengren的博客 3403

【C/C++ 函数 形参传递】C++中std::function传递深度解析:值传递与引用传递的底层原理

在现代编程实践中,C++以其强大的功能和高效的执行效率广受欢迎。特别是在多线程编程方面,C++ 提供了丰富的库和功能,让开发者能够有效地管理和执行并行任务。在这个背景下,`std::function`(标准函数)作为C++11中引入的一项功能,对于多线程编程尤为重要。

探索C++编程的奥秘,分享深入的技术见解和实践,旨在激发读者创造力与解决问题的思维。 2079

C/C++回调函数实现与std::function和std::bind介绍

回调函数是一种编程模式,指的是将一个函数作为参数传递给另一个函数,并在某个特定事件发生时或满足某些条件时由该函数调用。这种机制允许你定义在特定事件发生时应执行的代码,从而实现更灵活和模块化的程序设计。

new9232的博客 1372

[C++]std::function用法

值得注意的是,lambda表达式的类型并不是std::function,而是一种编译器自动生成的类,与std::function类似,lambda表达式也重载了operator(),但它们的类型和std::function并不一样。我个人的建议是优先使用std::function,因为他比起函数指针来可读性大大增加(C++函数指针的语法特别变态,特别是复杂了的话就非常难懂)。你认为T是什么类型?其实T是一个函数指针,指向的函数A返回值又是一个函数指针,指向函数B,A无参数,B的返回值是void,B无参数。

FL1768317420的博客 1145

function函数的用法_深入浅出C++的function

今天我们来聊聊C++的function。std::function是从C++11开始支持的特性,它起什么作用?又有什么好处呢?C语言中的函数指针对C语言熟悉的同学应该都知道,C语言中有一种高级技巧叫作函数指针,我们可以让函数指针指向参数类型相同、返回值类型也相同的函数。通过函数指针我们也可以实现C++中的多态。我们来看个例子:#include上面代码中定义了一个函数指针func,它可以指向无输入参...

weixin_39902345的博客 1万+

std::function 简介

std::function是C++标准库中的函数包装器,可存储、复制和调用多种可调用对象(函数、lambda表达式、绑定表达式、函数对象等)。若未初始化目标直接调用会抛出std::bad_function_call异常。它支持拷贝构造和赋值操作,提供成员类型(如返回值/参数类型)和操作函数(构造、析构、调用运算符等)。示例展示了其包装普通函数、lambda和仿函数的能力,通过统一接口实现灵活调用。该特性广泛应用于回调机制和泛型编程,需注意空对象检查以避免运行时异常。

人无远虑,必有近忧 2433

C++11中的std::function 简单易懂

在C++11中引入了std::function, 那么function有什么好处呢。 简而言之, std::function是对C++中各种可调用实体的封装,形成一个新的可调用的std::function对象。可调用实体是什么呢?C++中都有哪些可调用实体呢? 在C++中,可调用实体包括如下四类:   1、是一个函数指针。(函数必须和C函数一样可在编译期之内唯一确定的函数指针)   2、函数对象(也叫仿函数),即具有一个重载operator()成员函数的类对象。   3、是一个可被转换为函数指针的

姜的理想国 2740

C/C++|std::function 浅度解析

std::function 是 C++ 标准库中的一个通用多态函数包装器。它可以存储、复制和调用任意可调用目标(函数、lambda 表达式、绑定表达式或其他函数对象)。std::function 占有固定尺寸的内存,这是因为它的实现方式决定了这一点。让我们深入探讨这一点。

糖炒栗子 2008
上一篇: 高性能c++ string split实现
下一篇: 记录一次线上pthread_cond_broadcast引发的性能问题
Sweet_Oranges
博客等级 码龄12年 1粉丝 20原创
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

个

红包个数最小为10个

元

红包金额最低5元

当前余额3.43元 前往充值 >
需支付:10.00元
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付元
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值