質問をすることでしか得られない、回答やアドバイスがある。

15分調べてもわからないことは、質問しよう!

ただいまの
回答率

90.23%

C++の修飾子や指定子について

解決済

回答 1

投稿

  • 評価
  • クリップ 0
  • VIEW 1,784

strike1217

score 578

const int func(int a){...};  // 1

int const func(int a){...};  // 2

int func(int a) volatile {...}; // 3

1番と2番は全く同じ意味ですよね?
これは返り値がconstになる・・・??という意味ですか??

3番めはメンバ関数にできることですが、これは・・・この関数が呼び出されている間だけメンバ変数を最適化抑止するという意味ですか??

1番と2番については紛らわしくなりそうです。
例えば

constexpr int func(){...};


constexpr関数になりますが・・・これだと変数を修飾しているように見えませんか??

以下のほうが関数を修飾しているように見えません??

int constexpr func(){...};

逆に、以下のようにすると、関数全体を最適化抑止しているのかな??という風に見えませんか??

volatile int func(){...};


これも返り値が最適化抑止ということですよね??
なんか紛らわしいですね・・・

inlineにも同じことが言えそうなんですが・・・
noexceptもわかりにくいです。

int noexcept func(){...}; // ERROR!!! 前には書けない。


noexceptの場合は、上記はダメでした。
お尻のほうに書かないといけないようです。
例外を送出しない関数なら前に書いたほうが良いような気がするんですが・・・

リンク内容
mutable const volatile inline など細かく分類されているようです。

修飾子と指定子の違いがよく分かりません。
記述する場所もイマイチはっきりしていません。
先頭に記述する場合と後ろに記述する場合の違いがよくわからないです。

修飾したい対象のものの直前と統一すれば分かりやすいと考えています。
しかし実際にはそうなっていないですよね。

どなたか教えてください。
わかりにくい。
予約語によって記述箇所が異なるので、全パターン覚えないといけないんですかね?

環境は Linux 64bit gcc です。

  • 気になる質問をクリップする

    クリップした質問は、後からいつでもマイページで確認できます。

    またクリップした質問に回答があった際、通知やメールを受け取ることができます。

    クリップを取り消します

  • 良い質問の評価を上げる

    以下のような質問は評価を上げましょう

    • 質問内容が明確
    • 自分も答えを知りたい
    • 質問者以外のユーザにも役立つ

    評価が高い質問は、TOPページの「注目」タブのフィードに表示されやすくなります。

    質問の評価を上げたことを取り消します

  • 評価を下げられる数の上限に達しました

    評価を下げることができません

    • 1日5回まで評価を下げられます
    • 1日に1ユーザに対して2回まで評価を下げられます

    質問の評価を下げる

    teratailでは下記のような質問を「具体的に困っていることがない質問」、「サイトポリシーに違反する質問」と定義し、推奨していません。

    • プログラミングに関係のない質問
    • やってほしいことだけを記載した丸投げの質問
    • 問題・課題が含まれていない質問
    • 意図的に内容が抹消された質問
    • 広告と受け取られるような投稿

    評価が下がると、TOPページの「アクティブ」「注目」タブのフィードに表示されにくくなります。

    質問の評価を下げたことを取り消します

    この機能は開放されていません

    評価を下げる条件を満たしてません

    評価を下げる理由を選択してください

    詳細な説明はこちら

    上記に当てはまらず、質問内容が明確になっていない質問には「情報の追加・修正依頼」機能からコメントをしてください。

    質問の評価を下げる機能の利用条件

    この機能を利用するためには、以下の事項を行う必要があります。

回答 1

checkベストアンサー

+1

こんにちは。

constは型を修飾します。int const、const intはどちらも変更不可なint型の意味ですね。
メンバ関数の後ろに記述するconstは判りにくいですね。
メンバ関数は隠しパラメータとして*thisを持っています。その*thisの型を修飾しています。要するにthisの指す先をconst(変更不可)として扱います。

volatileはconstと同じく型を修飾します。メンバ関数の後ろに書いているのを見たことはないですが、同じことの筈です。thisの指す先をvolatileとして扱う筈です。この場合、volatileが有る時と無い時で何が変わるのか私は良く分かりません。何も変わらないような気もします。

その使い方のconstexprは関数を修飾します。陶芸家の中3女子の方の解説が詳しいです。
constexprの読み方はチュウサンジョシと言われる程です。

noexceptも関数を修飾します。これは覚えましょう。

予約語によって記述箇所が異なるので、全パターン覚えないといけないんですかね?

そういうことですね。数もたかがしれていますし、直ぐ慣れますよ。


【蛇足ですが】
個人的にはnoexceptはあまり使わない方がよいように思います。例外が飛んでくるのに間違って付けると例外が投げられた時、エラー情報が消えてしまうので。
コンパイラはnoexceptな関数が直接例外を投げないことしかチェックしてくれません。その関数が呼び出している関数が投げないことはチェックしてくれないのです。
noexcept関数内でtry-catchして例外情報を残すか、小さな関数でパッと見て例外が投げられないことが明確な場合のみしか付けるべきではないように思います。

#include <iostream>

void bar()
{
    throw 12345;
}

void foo() noexcept // ←このnoexceptをなくせば例外の内容が表示される
{
    bar();
}

int main()
{
    try
    {
        foo();
    }
    catch(int e)
    {
        std::cout << "catch(" << e << ")\n";
    }
}


wandbox

投稿

編集

  • 回答の評価を上げる

    以下のような回答は評価を上げましょう

    • 正しい回答
    • わかりやすい回答
    • ためになる回答

    評価が高い回答ほどページの上位に表示されます。

  • 回答の評価を下げる

    下記のような回答は推奨されていません。

    • 間違っている回答
    • 質問の回答になっていない投稿
    • スパムや攻撃的な表現を用いた投稿

    評価を下げる際はその理由を明確に伝え、適切な回答に修正してもらいましょう。

  • 2018/01/27 16:19

    どうも立ち位置の違いのような気がしてきました。
    私は、ここは教育の場ではなく対等な技術者間のQAの場と考えています。
    catsforepawさんの『私の主張は最初から一貫して「仕様の理解を促す」べきだということです。』からするとここは教育の場としての面が強いとお考えかもしれないですね。

    > 理解が進むのは喜ばしいことだと思うのですが

    それはその通りです。
    そして、確かに私はnoexceptを学習することを促していません。寧ろ否定し「noexceptは安易に使うな」と警鐘を鳴らしているだけです。
    しかし、ここは教育の場ではなく技術者間のQAの場と考えていますので、あまり知られていないリスクを告知するだけでも有用な行為と考えています。非難されるのは妥当ではないと感じています。

    私はcatsforepawさんの立ち位置を否定するつもりはありません。教育の場として捉えて動機づけまですることは歓迎されると思います。
    しかし、私はそこまでしなくてもteratailは有用と考えています。有用と考える情報を提供するまでで動機づけまでしない場合がほとんどです。catsforepawさんには、できれば私の立ち位置もご理解頂けると幸いです。

    > レベルの話が出ましたが、相手のそれをどうやって判断するのでしょうか。

    これは見ている方ご自身です。私は問題点を再現できる簡単なソースを提示しています。それを理解できるできないはご自身が判断されるでしょう。私ではありません。

    > 「間違えると困るから使うな」では、「どうせあんたが使うと間違えるだろうからとにかく使うな」と言っているように思えたからです。

    そのような意図は全くありません。メリット/デメリットを比較して機能の採用/不採用を決める方は、ご自身の裁量でメリットとデメリット情報を収集されると思います。私の説明とソースは、そのデメリット情報として有用と思います。見た方がご自身で検証できますので、決して一方的に「使うな」にはなっていないと思います。

    因みに、私自身はnoexceptを使うと直ぐにバグりそうです。使うためにはかなりの工数を割く必要があるので、よほど必要でない限り使いません。例外を流出させない苦労はデストラクタだけで十分お腹いっぱいと感じてます。

    キャンセル

  • 2018/01/27 18:08

    教育云々はあまり関係がありません。理解するには動機が必要であり、動機の妨げは理解の妨げと考えたまでです。教えるからには理解してほしいですから。

    ここに来てようやく議論の本質が見えてきました。これは「何をリスクと捉えるか」の見解の相違のようです。
    Chironianさんはnoexceptの使用をリスクと捉えているようですが、私はnoexceptの不理解をリスクと考えています。お互いリスク回避の方策をあれこれ書き連ねていたわけですね。

    strike1217 さん

    質問とは関係ないことを長々と書いてしまってすみませんでした。

    キャンセル

  • 2018/01/27 18:25

    あああ、なるほど。そういうことだったのですね!
    確かにstrike1217 さんには申し訳なかったです。

    キャンセル

15分調べてもわからないことは、teratailで質問しよう!

  • ただいまの回答率 90.23%
  • 質問をまとめることで、思考を整理して素早く解決
  • テンプレート機能で、簡単に質問をまとめられる

同じタグがついた質問を見る