C++的 long 是一个很尴尬的存在。 - V2EX
V2EX = way to explore
V2EX 是一个关于分享和探索的地方
现在注册
已注册用户请  登录
tool2dx
V2EX    编程

C++的 long 是一个很尴尬的存在。

  •  
  •   tool2dx 2024-06-27 13:06:41 +08:00 2398 次点击
    这是一个创建于 470 天前的主题,其中的信息可能已经有所发展或是发生改变。
    long 在 32 位编译器里,是 32 位整型。在 64 位编译器里,是 64 位整型。

    为了避免代码歧义,我一般会用 long long 来表示 64 位整型,这样不管 32 位还是 64 位编译,都能保持一致性。

    但是,官方有一个 INT64_C 的宏,是下面这样定义的。也就是官方推荐 64 位编译器,优先选用 long 为 64 位整型。


    #if defined(__LP64__)
    #define INT64_C(c) c ## L
    #else
    #define INT64_C(c) c ## LL
    #endif


    这就很尴尬了,我代码里全部都是 long long ,和 long 并不兼容,属于两个不同类型。

    最后决定,我不用官方的 INT64_C 宏了,属于把人带偏的节奏。
    15 条回复    2024-06-27 16:48:53 +08:00
    blinue
        1
    blinue  
       2024-06-27 13:13:11 +08:00   2
    需要 64 位用 int64_t 就好,现代 C++ 基本淘汰了 long 和 long long
    leeside
        2
    leeside  
       2024-06-27 13:21:52 +08:00
    @blinue 赞同
    tool2dx
        3
    tool2dx  
    OP
       2024-06-27 13:24:37 +08:00
    @blinue 这是一回事好吧。

    你去看看最新的 stdint.h 头文件里,int64_t 就是用 long 和 long long 来定义的。

    #if defined(__LP64__)
    typedef long __int64_t;
    #else
    typedef long long __int64_t;
    #endif

    typedef __int64_t int64_t;
    dnfQzjPBXtWmML
        4
    dnfQzjPBXtWmML  
       2024-06-27 13:30:22 +08:00
    用[u]intXX_t 就可以完美保证一致性,不清楚你对 INT64_C 和 int64_t 的偏见是哪来的
    blinue
        5
    blinue  
       2024-06-27 13:33:52 +08:00
    @tool2dx #3 标准只要求 long 至少 32 位,long long 至少 64 位,具体多长是编译器决定的。要保证一致性最好用 int64_t
    passive
        6
    passive  
       2024-06-27 13:36:00 +08:00 via Android
    常年开着 -Wlong-long 写代码,
    long 的用途只限于 long double 。
    a33291
        7
    a33291  
       2024-06-27 13:37:42 +08:00
    msvc14(vs2022)上定义是这样

    typedef long long int64_t;
    lunafreya
        8
    lunafreya  
       2024-06-27 13:42:13 +08:00
    不是一回事, `__LP64__`
    ivvei
        9
    ivvei  
       2024-06-27 13:45:55 +08:00
    要精确稳定表示 64 位那就用 int64_t , 不会有任何歧义和不一致。
    StarsunYzL
        10
    StarsunYzL  
       2024-06-27 13:53:32 +08:00   4
    标准本身就有保持一致性的 (u)int64_t 来表示 64 位整型,不清楚为啥你非要用 long long 来表示 64 位整型还要保持一致性,这就很尴尬
    inhzus
        11
    inhzus  
       2024-06-27 14:31:33 +08:00
    为了避免代码歧义,我一般会用 **u?int64_t** 来表示 64 位整型,这样不管 32 位还是 64 位编译,都能保持一致性

    不关心 size ,用 int ,关心 size 用 u?int(16|32|64)_t
    xylxAdai
        12
    xylxAdai  
       2024-06-27 14:55:03 +08:00
    都看编译器实现的。不然 long long 一样可以给你用 32 位存
    ho121
        13
    ho121  
       2024-06-27 15:16:31 +08:00 via Android
    @tool2dx 不能只看某一个编译器对 int64_t 的定义。
    long long 的问题是,标准没有明确一定是 64 位。而 int64_t 虽然是个宏,却能保证不同编译器的不同实现下,一定被定义成 64 位的。
    zzzlight
        14
    zzzlight  
       2024-06-27 16:29:02 +08:00
    CPP 就是这样 看编译器看系统环境 不止 long... 这些各种宏搞得人都容易搞混了 这坑前几年踩好多次了,以为是 64 位发现是 32 位
    slack
        15
    slack  
       2024-06-27 16:48:53 +08:00 via Android
    移植这种代码也是最困难的,这些玩意也是历史遗留下来的玩意没法改。
    关于     帮助文档     自助推广系统     博客     API     FAQ     Solana     2171 人在线   最高记录 6679       Select Language
    创意工作者们的社区
    World is powered by solitude
    VERSION: 3.9.8.5 26ms UTC 16:10 PVG 00:10 LAX 09:10 JFK 12:10
    Do have faith in what you're doing.
    ubao snddm index pchome yahoo rakuten mypaper meadowduck bidyahoo youbao zxmzxm asda bnvcg cvbfg dfscv mmhjk xxddc yybgb zznbn ccubao uaitu acv GXCV ET GDG YH FG BCVB FJFH CBRE CBC GDG ET54 WRWR RWER WREW WRWER RWER SDG EW SF DSFSF fbbs ubao fhd dfg ewr dg df ewwr ewwr et ruyut utut dfg fgd gdfgt etg dfgt dfgd ert4 gd fgg wr 235 wer3 we vsdf sdf gdf ert xcv sdf rwer hfd dfg cvb rwf afb dfh jgh bmn lgh rty gfds cxv xcv xcs vdas fdf fgd cv sdf tert sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf shasha9178 shasha9178 shasha9178 shasha9178 shasha9178 liflif2 liflif2 liflif2 liflif2 liflif2 liblib3 liblib3 liblib3 liblib3 liblib3 zhazha444 zhazha444 zhazha444 zhazha444 zhazha444 dende5 dende denden denden2 denden21 fenfen9 fenf619 fen619 fenfe9 fe619 sdf sdf sdf sdf sdf zhazh90 zhazh0 zhaa50 zha90 zh590 zho zhoz zhozh zhozho zhozho2 lislis lls95 lili95 lils5 liss9 sdf0ty987 sdft876 sdft9876 sdf09876 sd0t9876 sdf0ty98 sdf0976 sdf0ty986 sdf0ty96 sdf0t76 sdf0876 df0ty98 sf0t876 sd0ty76 sdy76 sdf76 sdf0t76 sdf0ty9 sdf0ty98 sdf0ty987 sdf0ty98 sdf6676 sdf876 sd876 sd876 sdf6 sdf6 sdf9876 sdf0t sdf06 sdf0ty9776 sdf0ty9776 sdf0ty76 sdf8876 sdf0t sd6 sdf06 s688876 sd688 sdf86