質問: 0;i < 5;i ++) { Output_game(data[i]); } return 0; } void Input_game(game *data) { scanf("%s",data->name); /* nameが配列名なので、&は必要ない 。*/ scanf("%d",&data->release); /* releaseが変数名なので&をつける...?*/ /*32行目*/ scanf("%s",data->genre); /* nameと同様 */ return 0; } void Output_game(game data) { printf("作品名:%s 発売年:%d ジャンル:%s\n",data.name,data.release,data.genre); return 0; } ``` ### 追加の質問 「苦しんで覚えるC言語」の次に読んでみると、参考になるかもしれない書籍がありましたら 教えていただきたいです。 (こちらは本当におまけですので、無理に答えていただなくても大丈夫です。) よろしくお願いします...!
回答: (1)はすでにアドレスですので、`data`のままいいです。`&*data`はdataが示す値を取得して、その値が存在する場所のアドレス(結局はdataそのもの)になるため、意味が無い演算です。よく`scanf`で`&`を付けるのはポインタを指定しなければならないからで、既にポインタの場合はそのままでかみません。 (2)で注意すべきなのは演算子の優先順位とその優先順位が高いところから値を求めていく点です。演算子の優先順位は下記を参考にしてください。 Wikipedia:CとC++演算子#演算子の優先順位 上からわかるように`&`と`->`は`->`の方が結合が強いため、先に計算されます。わかりやすく()をつけると `&data->release` ↓ `&(data->release)` ↓ `&((*data).release)` となります。つまり、上記の動作は()の内側から計算されるため、 1. dataが示す先の構造体を得る `*data` 2. 1.の構造体の中のreleseを得る `(*data).relese` 3. 2.で得た値が存在する場所のアドレスを得る `&((*data).relese)` という動作になります。 (おまけ)古典ですが聖典「K&R」は一度は読んでおくと良いかもしれません。内容は古いですが、C言語を作った開発者によるC言語のエッセンスが詰まっています。ただ、全く初心者向けではないため、一度読んだだけで全て理解するのは難しいです。ある程度やってから再度読み直すと、その素晴らしさに気付くことでしょう。