数学研发论坛

 找回密码
 欢迎注册
查看: 210|回复: 14

[讨论] std::strong_ordering 该是 class,还是 struct?

[复制链接]
发表于 2020-12-24 16:02:50 | 显示全部楼层 |阅读模式

马上注册,结交更多好友,享用更多功能,让你轻松玩转社区。

您需要 登录 才可以下载或查看,没有帐号?欢迎注册

x
为什么有此一问?

在疫情歇业期间,我曾发了个帖子:发现微软编译器三路比较运算(<=>)的一个大 bug!


现在又发现一个跟此相关的新问题:

由于工作忙,业余项目暂停了好久,期间 VS2019 曾有过多次升级,包括对上述 bug 的修复,
早上心血来潮,把那个项目试着重新编译一下,居然通不过!怎么着都编译不过!
警告为:error LNK2001: 无法解析的外部符号 "class std::strong_ordering ..."

奇了怪了!我打开 #include <compare>,搜索关键字“strong_ordering”,代码片段如下:

  1. inline constexpr weak_ordering weak_ordering::less{static_cast<_Compare_t>(_Compare_ord::less)};
  2. inline constexpr weak_ordering weak_ordering::equivalent{static_cast<_Compare_t>(_Compare_eq::equivalent)};
  3. inline constexpr weak_ordering weak_ordering::greater{static_cast<_Compare_t>(_Compare_ord::greater)};

  4. // CLASS strong_ordering
  5. struct strong_ordering {
  6.     static const strong_ordering less;
  7.     static const strong_ordering equal;
  8.     static const strong_ordering equivalent;
  9.     static const strong_ordering greater;

  10.     constexpr operator partial_ordering() const noexcept {
  11.         return {static_cast<_Compare_t>(_Value)};
  12.     }
复制代码


这个代码显示的 strong_ordering 是 struct,提示怎么说是 class ?
这才意识到,我的 dll 是以 def 文件导出的,可能是导出接口发生了改变,
试着将 .def 文件中的“AVstrong_ordering”字串替换成“AUstrong_ordering”,再编译,就通过了!

这肯定是微软中途曾变更过它的声明方式,从 class 变更成了 struct(上述代码中,还特别保留了一行注释“// CLASS strong_ordering”),
其中之一肯定不符合标准规范。

但标准规范又是什么呢?class?struct?
查阅:std::strong_ordering,里面的规定是 class!

对于 C++ 来说,两者并没有本质区别,
但对于导出接口来说,它们就有区别了!

不知微软为何要将它从 class 变更到 struct,会不会再变回去?

点评

两者性能应无差异  发表于 2020-12-30 09:28
struct性能更好点?  发表于 2020-12-30 08:19
毋因群疑而阻独见  毋任己意而废人言
毋私小惠而伤大体  毋借公论以快私情
发表于 2020-12-25 16:14:50 | 显示全部楼层
能不要升级就不要升级!
要保持编译程序的稳定!
稳定压倒一切!不折腾!
我以前也喜欢升级软件,而我现在写代码都注明运行软件的版本!
毋因群疑而阻独见  毋任己意而废人言
毋私小惠而伤大体  毋借公论以快私情
 楼主| 发表于 2020-12-25 16:41:23 | 显示全部楼层
对不起,我跟你不同,作为开发者,我就喜欢用最新最炫最标准的技术。
毋因群疑而阻独见  毋任己意而废人言
毋私小惠而伤大体  毋借公论以快私情
发表于 2020-12-25 17:10:48 | 显示全部楼层
恩, 其实我也是追新党
我现在用的笔记本同时安装了最新的macos 11.1.  Windows 10 20H2, Manjaro Linux 20.2.
然后凡是用到某工具,某软件第一反映就是 升级一下,看看是不是错过新版本了。。。
我连我的系统引导工具opencore,我都有时不时 的换成最新的版本。。。
并乐在其中。

点评

manjaro+1  发表于 2020-12-25 21:45
毋因群疑而阻独见  毋任己意而废人言
毋私小惠而伤大体  毋借公论以快私情
发表于 2021-1-4 12:05:52 | 显示全部楼层
也有可能是开始用错了类型,一般AV开头的是媒体库定义的类,一般struct里定义的是纯数据类型,或是比较简单的数据操作。不知道是不是这样。
毋因群疑而阻独见  毋任己意而废人言
毋私小惠而伤大体  毋借公论以快私情
 楼主| 发表于 2021-1-4 15:42:43 | 显示全部楼层
灵树 发表于 2021-1-4 12:05
也有可能是开始用错了类型,一般AV开头的是媒体库定义的类,一般struct里定义的是纯数据类型,或是比较简单 ...

原因与上述无关。

这是由 C++ 编译时函数名修饰约定规则决定的:

修饰名是编译器在编译函数定义或者原型时生成的字符串。

参数表的拼写代号表示:
X--void
D--char
E--unsigned char
F--short
H--int
I--unsigned int
J--long
K--unsigned long(DWORD)
M--float
N--double
_N--bool
U--struct
V--class

PA--表示指针
PB--表示const类型的指针
...

点评

不确定,希望能统一。如果标准不统一话,对于 exe 来说,反正是内部的事,无所谓;对于动态库来说,可以“伪造”相应的 lib 文件解决。  发表于 2021-1-5 07:46
这个命名规则有统一的规范吗?不同的c++编译器可能会用不同的命名规则吧?  发表于 2021-1-4 16:56
毋因群疑而阻独见  毋任己意而废人言
毋私小惠而伤大体  毋借公论以快私情
发表于 2021-1-11 09:54:15 | 显示全部楼层
我以前用vim写脚本,但是vim升级后,软件的特性就改变了,不仅仅是vim,
我以前画图,看到老员工用很老版本的AutoCAD,然后我用最新版本的AutoCAD,然后我就觉得老员工很落后,跟不上时代,
后来有一天,我终于领悟到:不是老员工落伍,而是老员工追求软件的稳定性,不仅仅是软件运行的稳定性,还与软件的特性的稳定性、操作习惯的稳定性!
而这些稳定性,随着升级很可能被打破,需要重新适应!
所以我后来写脚本,一概注明编写脚本软件的版本,运行脚本软件的版本,以及操作系统的版本,然后我也讨厌升级了!
我终于变成了我被曾经的自己所鄙视的“老同志”!

点评

有时候还需要注明是utf-8编码,还是cp936编码!比如手机vcf通讯录一般需要utf8编码,后来我找到更好的解决办法了!  发表于 2021-1-11 10:01
毋因群疑而阻独见  毋任己意而废人言
毋私小惠而伤大体  毋借公论以快私情
发表于 2021-1-11 11:46:16 | 显示全部楼层
追求稳定而不去升级很正常,但并不一定是个好的做法。
软件升级,很多时候是增加了新的特性,如果不使用这些新的东西,一直使用旧版本确实没问题。但时间长了,很多情况是你不得不更新。而这时不论是软件本身,还是操作习惯都已经变化巨大了,重新适应其实更痛苦,还不如定期更新,不一定要追求最新,但至少不能太落伍。
windows的兼容性是一流的,十几年前的软件至今还能运行,你一定要停留在十几年前也还问题不大。
linux可就没这么友好了,老的软件包现在已经不好找,即使找到也不容易编译,一大推的依赖包都要找老版本,编译成了也不一定能正常使用。

如今飞速发展的科技,就是一辆高速列车,不抓紧了,必定被甩下车去……

点评

有道理,不过软件除非更新的功能我很需要,否则一些对我来说鸡肋(但对别人不一定)性质的功能,我都懒得更新的。如果遇到很需要的功能,我确实会去更新。  发表于 2021-1-15 14:58
毋因群疑而阻独见  毋任己意而废人言
毋私小惠而伤大体  毋借公论以快私情
您需要登录后才可以回帖 登录 | 欢迎注册

本版积分规则

小黑屋|手机版|数学研发网 ( 苏ICP备07505100号 )

GMT+8, 2021-1-28 02:52 , Processed in 0.067053 second(s), 17 queries .

Powered by Discuz! X3.4

© 2001-2017 Comsenz Inc.

快速回复 返回顶部 返回列表