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

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

新規登録して質問してみよう
ただいま回答率
85.48%
C++11

C++11は2011年に容認されたC++のISO標準です。以前のC++03に代わるもので、中枢の言語の変更・修正、標準ライブラリの拡張・改善を加えたものです。

C++

C++はC言語をもとにしてつくられた最もよく使われるマルチパラダイムプログラミング言語の1つです。オブジェクト指向、ジェネリック、命令型など広く対応しており、多目的に使用されています。

Q&A

解決済

1回答

968閲覧

constexprについての確認

apa

総合スコア68

C++11

C++11は2011年に容認されたC++のISO標準です。以前のC++03に代わるもので、中枢の言語の変更・修正、標準ライブラリの拡張・改善を加えたものです。

C++

C++はC言語をもとにしてつくられた最もよく使われるマルチパラダイムプログラミング言語の1つです。オブジェクト指向、ジェネリック、命令型など広く対応しており、多目的に使用されています。

0グッド

0クリップ

投稿2020/10/19 08:02

constexprについて
およびコンパイル時関数についての質問なのですが、

constexpr int num(int a, int b){return a + b;}

int main
{
int i = num( 1 + 5); ←はコンパイル時関数として処理される

int ii = 0;
scanf("%d",&ii);
ii = num(ii + ii); ←の場合はコンパイル時関数ではない?
}

↑の考え方が正しければ、コンパイル関数は
コンパイル時に引数が未知でない関数が呼ばれたときはコンパイル時関数が発動するという認識であっていますでしょうか?

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

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

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

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

guest

回答1

0

ベストアンサー

いいえ。 質問の例ではどちらも実行時に呼び出されます。

constexpr が呼出されるのが実行時かコンパイル時かを決定づけるのは引数ではなく「その関数の結果を受け取る側」です。 定数式が要求されている場に現れるときにコンパイル時に呼び出されることになっています。

ただし、そのような言語上の理屈とは別に最適化による定数畳み込みがかかって定数になることはあります。


定数式が要求される文脈として代表的なものは

  • constexpr 指定が付いた変数の初期化
  • 配列を宣言するときの要素数
  • テンプレート引数に渡す値

があります。


変数に constexpr を付けるのが定数式の文脈のコントロールとして最もわかりやすいと思うのでそれを元に例を示します。

cpp

1#include <iostream> 2 3constexpr int num(int a, int b) { 4 return a + b; 5} 6 7int main(void) { 8 int x = num(1, 5); // ← このとき num は実行時に呼び出される 9 constexpr int y = num(1, 5); // ← このとき num はコンパイル時に呼ばれる 10 constexpr int z = num(x, x); // ← このとき num はコンパイル時に呼ばれるが x は定数式ではないのでエラー 11 12 std::cout << x << y << z << std::endl; 13}

投稿2020/10/19 08:29

編集2020/10/19 14:18
SaitoAtsushi

総合スコア5446

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

apa

2020/10/19 12:35 編集

int i = num( 1 + 5); ← つまりこういう場合はってことですね?  (引数が決まってなくとも受け皿ができていればOK) となるとすべての処理がコンパイル時に行える気がして 逆にできない処理の想像ができないのですが。。
SaitoAtsushi

2020/10/19 13:06

私が述べたのは「実行時かコンパイル時かを決定する」のが受け取る側であると述べているのであって、引数が定数式でなくてよいというわけではありません。 コンパイル時に呼び出される文脈にもかかわらず引数が定数式でないならコンパイルエラーになるので実行時にもコンパイル時にも呼び出されません。
apa

2020/10/19 13:56

自分の返答の仕方が分かりづらくてすいません。 受け取る側が実行時と判断する場面が想像できないということです コンパイル時に呼び出される文脈にもかかわらず引数が定数式でないならコンパイルエラーになるので実行時にもコンパイル時にも呼び出されません ←はscanfのように実行時にしかわからない変数が入れられてしまったときにエラーを吐くよということでしょうか? scanfのほうはとおったので大丈夫だと思ったのですが、
SaitoAtsushi

2020/10/19 14:05

はい。 scanf などの外部から入力した値は当然ですが定数式になりえません。 この質問の例においては ii へ代入するというのは右辺が定数式であることを要求しないので num は実行時に呼び出されますし、その引数も定数式である必要はありません。
guest

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

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

ただいまの回答率
85.48%

質問をまとめることで
思考を整理して素早く解決

テンプレート機能で
簡単に質問をまとめる

質問する

関連した質問