文字列リテラルの初期化から統一初期化構文と複合リテラルへの話

@melponnの「char* p = "hoge"; はできないけど char p[] = "hoge"; はできる」という旨の発言から、g++でコンパイルできる(int[]){1,2,3}はC++0xでどういう扱いなのかという話へ飛び移った3月10日深夜のC++TL。なお、(int[]){1,2,3}はC++0xの構文ではなく、g++でもC99の複合リテラルとして解析されているだろうという結論に至りました。
3
めるぽん.c @melponn

C++0x で char* p = "hoge"; はできないけど char p[] = "hoge"; はできるっぽい?そうなると array-to-pointer 変換で char* にもできそうな気がするけど・・・

2010-03-11 01:19:09
Egtra (ysk-noh) @egtra

@melponn char p[] = "hoge";はchar p[] = {'h','o','g','e','\0'};の糖衣構文と考えれば、int a[] = {1,2,3}; int* p = a;ができてもint* p = {1,2,3};がダメなのと同じ理屈だと思う

2010-03-11 01:25:59
@monimura

あれ、p[] って、終端の NULL 文字も入ったっけ?

2010-03-11 01:27:45
@monimura

const char p[] かな?あれ?

2010-03-11 01:28:29
@monimura

そうか、"hoge" という文字列リテラルで初期化しているから、終端の NULL 文字も入るのかな。

2010-03-11 01:31:40
@monimura

明日、忘れていなかったら自分でなんとか確認しよう。

2010-03-11 01:32:16
めるぽん.c @melponn

そもそも string literal が array of n const char なのにどこの仕様で char[] に格納できようになってるのかも気になって仕方がない・・・

2010-03-11 01:33:11
めるぽん.c @melponn

うお、§8.5.2 におもっきし char array は string literal で初期化できるって書いてる・・・

2010-03-11 01:38:37
めるぽん.c @melponn

ああ、なるほど、これで初期化することはできるけど、string literal 自体は const char[] だから char* への変換はできないのね。

2010-03-11 01:40:17
Egtra (ysk-noh) @egtra

うひょー、int *p = (int[]){1, 2, 3, 4};ってコードがC99だけでなくC++0xでも通るのか?g++ 4.4.1でエラーにならないぞ。

2010-03-11 01:40:36
はざまwithあかりんかわかわ @hazama_akkarin

なんだ、この呪文みたいなコードはRT: @egtra: うひょー、int *p = (int[]){1, 2, 3, 4};ってコードがC99だけでなくC++0xでも通るのか?g++ 4.4.1でエラーにならないぞ。

2010-03-11 01:46:27
七誌 @7shi

@egtra g++ 3.3だとエラーで、g++ 4.2.4では通ることを確認しました。

2010-03-11 01:49:59
Egtra (ysk-noh) @egtra

@DecimalBloat ええ、C99とは構文の扱いが異なるということでしょうか。

2010-03-11 01:50:20
IGARASHI Shinji@無職 @s50

initializer listについてかるくしらべてみる

2010-03-11 01:53:50
でちまるさん(実際かわいい) @decimalbloat

規格を読んでも int * p = (int[]){1,2,3}; が well-formed である理由は見あたらない…

2010-03-11 02:19:26
IGARASHI Shinji@無職 @s50

うおお!?そういやC99のCompound Literalはlvalueだたーのか

2010-03-11 02:20:29
IGARASHI Shinji@無職 @s50

あっちはキャストじゃないんだよなあ

2010-03-11 02:21:24
でちまるさん(実際かわいい) @decimalbloat

braced-init-list が literal として認識されてるのか?

2010-03-11 02:24:47
めるぽん.c @melponn

あれ、§8.5.1¶7の例って不適切じゃないのか?

2010-03-11 02:28:33
IGARASHI Shinji@無職 @s50

int *p = ((int[]){1,2});これ試しにg++4.3.3に食わしてみたけど、ポインタ経由でp[0]++とかもできるですね

2010-03-11 02:31:06
めるぽん.c @melponn

"asdf" が char* に変換されてる。

2010-03-11 02:31:26
Egtra (ysk-noh) @egtra

(int[]){1, 2, 3}がC++0xで合法だったとして、おそらくスコープは一時オブジェクトだよなあと想像。これからドラフト見てくる。

2010-03-11 02:38:49
IGARASHI Shinji@無職 @s50

お禿げ様はC99 style initializersはWe don’t propose to accept themとか言ってるようだけども?struct S{int x;}; S *p= &((S){1};はさすがに一時オブジェクトのあどれすーって警告出る(gccでは出ない)

2010-03-11 02:42:18
めるぽん.c @melponn

{ 1, 2, 3} 自体が何の型になるのかが仕様から分からない・・・

2010-03-11 02:45:08