先说结论,lambda是不能重载的(至少到c23依旧如此,以后会怎么样没人知道)。而且即使代码完全一样的两个lambda也会有完全不同的类型。 但虽然不能直接实现lambda重载,我们有办法去模拟。 在介绍怎么模拟之前,我们先看看c里的functor是怎么重载的。 首先类的函数调用运算符是可以重载的,可以这样写: structFunctor{ booloperator()(inti)const { returni%20; } booloperator()(conststd::string&s)const { returns.size()%20; } }; 在此基础上,c11还引入了...

  yZdUbUDB8h5t   11天前   19   0   0 C++

最近在翻《c函数式编程》的时候看到有一小节在说c14新增了“菱形运算符”。我寻思c里好像没什么运算符叫这名字啊,而且c14新增的功能很少,我也不记得有添加这种语法特性。一瞬间我有些怀疑我的记忆了,所以为了查漏补缺,我写了这篇文章。 什么是菱形运算符 这个概念在Java里比较多见: List<String>myList=newArrayList<>(); 这东西在Java里的学名是diamondoperator,表示使用泛型类并且类型参数在左侧的表达式已给出因此在右侧可以省略。 简单的说就是让你少写几次重复的类型参数。因为看起来像个菱形所以得名菱形运算符。 然后我们偶尔...

  yZdUbUDB8h5t   17天前   28   0   0 C++

今天讲一个常见的gccompiler(也就是官方版本的go编译器和runtime)在垃圾回收的扫描标记阶段做的优化。 我对这个优化的描述印象最深的是在bigcache的注释里,大致内容是如果map的键值都不包含指针,那么gc扫描的时候不管这个map多大都不会深入扫描map内部存储的数据,只检查map本身是否需要回收。 这么做的好处显然是可以让gc的扫描速度大大增加,从而减少gc对性能的损耗。 减少指针数量本身就是常见的优化手段,但让我感到好奇的是注释里说的“跳过”。跳过的依据究竟是什么,以及只有map存在这种跳过吗? 于是我进行了全面的搜索,结果除了复读bigcache里那段话的,没什么有用的...

  yZdUbUDB8h5t   2024年03月25日   37   0   0 Go

errgroup想必稍有经验的golang程序员都应该听说过,实际项目中用过的也应该不在少数。它和sync.WaitGroup类似,都可以发起执行并等待一组协程直到所有协程运行结束。除此之外errgroup还可以在协程出错时取消当前的context,以及它还能控制可运行的协程的数量。 但在日常的代码review时我注意到了几个比较常见的问题,这些问题有的无伤大雅最多只会造成一些性能损失,有的则会导致资源泄露甚至是死锁崩溃。 这里对这些比较典型的误用做下记录。 多余的context嵌套 先说个不是很常见但我还是遇到过两三次的不太妥当的用法。 我们知道errgroup在协程返回错误的时候会取消掉创...

  yZdUbUDB8h5t   2024年02月19日   85   0   0 Go

这篇文章并不讨论chan因为加锁解锁以及为了维持内存模型定义的行为而付出的运行时开销。 这篇文章要探讨的是chan在接收和发送数据时因为“复制”而产生的开销。 在做性能测试前先复习点基础知识。 本文索引 数据是如何在chan里流动的 情况1:发送的数据有读者在读取 情况2:发送的数据没有读者在读取 特例中的特例 为什么要复制 复制导致的开销 如何避免开销 只传小对象 只传指针 使用lock-free数据结构替代chan 开销可以接受的情况 总结 数据是如何在chan里流动的 首先我们来看看带buffer的chan,这里要分成两类来讨论。那没buffer的chan呢?后面会细说。...

  yZdUbUDB8h5t   2024年01月17日   18   0   0 Go

static_assert是c11添加的新语法,它可以使我们在编译期间检测一些断言条件是否为真,如果不满足条件将会产生一条编译错误信息。 使用静态断言可以提前暴露许多问题到编译阶段,极大的方便了我们对代码的排错,提前将一些bug扼杀在摇篮里。 然而有时候静态断言并不能如我们预期的那样工作,今天就来看看这些“不正常”的情况,我将举两个例子,每个都有一定的代表性。 为什么我的static_assert不工作 基于静态断言可以在编译期触发,我们希望实现一个模板类,类型参数不能是int,如果违反约定则会给出编译错误信息: template<typenameT> structObj{ sta...

  yZdUbUDB8h5t   2023年11月02日   27   0   0 C++

最近在看标准库里的type_traits的时候发现了个有趣的地方,几乎所有在标准库里的变量模板都是inline的! 不仅常见的实现上(libstdc、libc、msstl)都是inline的,标准里给的形式定义也是inline的。 比如微软开源的stl实现:https://github.com/microsoft/STL/blob/main/stl/inc/type_traitsL73 _EXPORT_STDtemplate<class_Trait> _INLINE_VARconstexprboolnegation_v=negation<_Trait>::value; ...

  yZdUbUDB8h5t   2023年11月02日   28   0   0 C++

去年看到字节跳动给golang提了issue建议把map的底层实现改成SwissTable的时候,我就有想写这篇博客了,不过因为种种原因一直拖着。 直到最近遇golang官方开始讨论为了是否要接受SwissTable作为map的默认实现,以及实际遇到了一个hashtable有关的问题,促使我重新思考了常见的hashtable算法,并决定写下这篇文章。 友情提示:本文不会从零教你写hashtable或者swisstable,并且需要你对hashtable有一点了解(至少用过且知道常用操作的时间复杂度);文中给出的示例代码为了简单易懂,放弃了一些实现细节上的优化,所以会和一些现成的实现不一样,还请...

  yZdUbUDB8h5t   2023年11月02日   44   0   0 C++

这是golang拾遗系列的第六篇。这个系列主要用来记录一些平时不常见的知识点,偶尔也会实现些有意思的小功能,比如这篇。 golang拾遗系列目录: golang拾遗:指针和接口 golang拾遗:为什么我们需要泛型 golang拾遗:嵌入类型 golang拾遗:内置函数len的小知识 golang拾遗:自定义类型和方法集 golang拾遗:实现一个不可复制类型 在本篇中我们将实现一个无法被复制的类型,顺便加深对引用类型、值传递以及指针的理解。 阅读本文前需要你拥有一定的前置知识,包括掌握基本的golang语法,能理解并应用接口,对sync包下的内容有粗略的了解。如果你准备好了,就可以接着往...

  yZdUbUDB8h5t   2023年11月02日   129   0   0 Go

对于无类型常量,可能大家是第一次听说,但这篇我就不放进拾遗系列里了。 因为虽然名字很陌生,但我们每天都在用,每天都有无数潜在的坑被埋下。包括我本人也犯过同样的错误,当时代码已经合并并发布了,当我意识到出了什么问题的时候为时已晚,最后不得不多了个合并请求留下了丢人的黑历史。 为什么我要提这种尘封往事呢,因为最近有朋友遇到了一样的问题,于是勾起了上面的那些“美好”回忆。于是我决定记录一下,一来备忘,二来帮大家避坑。 由于涉及各种隐私,朋友提问的代码没法放出来,但我可以给一个简单的复现代码,正如我所说,这个问题是很常见的: packagemain import"fmt" typeSstring ...

  yZdUbUDB8h5t   2023年11月02日   58   0   0 Go

最近翻开源代码的时候看到了一种很有意思的switch用法,分享一下。 注意这里讨论的不是typedswitch,也就是case语句后面是类型的那种。 直接看代码: func(ssystemd)Status()(Status,error){ exitCode,out,err:=s.runWithOutput("systemctl","is-active",s.unitName()) ifexitCode0&&err!=nil{ returnStatusUnknown,err } switch{ casestrings.HasPrefix(out,"active")...

  yZdUbUDB8h5t   2023年11月02日   32   0   0 Go

今天讲讲怎么让golang程序生成coredump文件,并且进行调试的。 别看我写了不少golang的博客,其实我平时写c的时间更多,所以也算和coredump是老相识了。coredump文件实际上是进程在某个时间点时的内存映像,当时进程使用的内存是啥样就会被原样保存下来存在文件系统的某个位置上,这个时间点一般是触发了SIGSEGV或者SIGABRT这两个信号的时候,当进程的内存映像保存完毕后进程就会异常终止,也就是大家喜闻乐见的“程序崩了”和“段错误:核心已转储”。 因此coredump就像是程序出错崩溃后的“第一现场”,是用来排查错误的主要资源。 不过我很少在golang里调试coredu...

  yZdUbUDB8h5t   2023年11月02日   30   0   0 Go

golang的泛型已经出来了一年多了,从提案被接受开始我就在关注泛型了,如今不管是在生产环境还是开源项目里我都写了不少泛型代码,是时候全面得回顾下golang泛型的使用体验了。 先说说结论,好用是好用,但问题也很多,有些问题比较影响使用体验,到了不吐不快的地步了。 这篇文章不会教你泛型的基础语法,并且要求你对golang的泛型使用有一定经验,如果你还是个泛型的新手,可以先阅读下官方的教程,然后再阅读本篇文章。 泛型的实现 实现泛型有很多种方法,常见的主流的是下面这些: 以c为代表的,类型参数就是个占位符,最后实际上会替换成实际类型,然后以此为模板生成实际的代码,生成多份代码,每份的类型都不一...

  yZdUbUDB8h5t   2023年11月02日   52   0   0 Go

经过了半年左右的开发,golang1.21在今天早上正式发布了。 这个版本中有不少重要的新特性和变更,尤其是在泛型相关的代码上。 因为有不少大变动,所以建议等第一个patch版本也就是1.21.1出来之后再进行升级,以免遇到一些意外的bug带来麻烦。 好了,一起来看看1.21带来的新特性吧。 本文索引 新的内置函数 类型推导更加智能 panic的行为变化 modules的变化 包初始化顺序的改变 编译器和runtime的变化 新标准库 log/slog和testing/slogtest slices和maps cmp 已有的标准库的变化 bytes context crypto/sh...

  yZdUbUDB8h5t   2023年11月02日   77   0   0 Go

PEP703是未来去除GIL的计划,当然现在提案还在继续修改,但大致方向确定了。 对于实现细节我没啥兴趣多说,挑几个我比较在意的点讲讲。 尽量少依赖原子操作的引用计数 没了GIL之后会出现两个以上的线程同时操作同一个Python对象的情况,首先要解决的是引用计数的计算不能出岔子,否则整个内存管理就无从谈起了。 多线程间的引用计数有很多现成方案了,比如c的shared_ptr ,还有rust的Arc 。这些方案都使用原子操作来维护引用计数并保证线程安全。 但原子操作是有代价的,虽然比mutex要小,但依旧会产生不少的性能倒退,这也是为什么c里一般不推荐多用shared_ptr<T>的...

  yZdUbUDB8h5t   2023年11月02日   292   0   0 Python
关注 更多

空空如也 ~ ~

粉丝 更多

空空如也 ~ ~