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

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

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

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

C++

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

Q&A

解決済

3回答

1222閲覧

非配列オブジェクトを指すポインタが配列の先頭を指すポインタと互換性を持つ条件

SaitoAtsushi

総合スコア5684

C++11

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

C++

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

0グッド

0クリップ

投稿2020/02/26 02:08

一文字 (char) を文字列 (std::string) にするにあたってこのような書き方は言語仕様上は許されますか?

#include <string> int main(){ char c = 'a'; std::string s(&c, 1); return 0; }

それというのも、 C++11 の「5.7 Additive operators」にはこのような文面があるからです。

(略)

additive-expression: multiplicative-expression additive-expression + multiplicative-expression additive-expression - multiplicative-expression

(略)

For the purposes of these operators, a pointer to a nonarray object behaves the same as a pointer to the first element of an array of length one with the type of the object as its element type.

(略)

配列ではないオブジェクトへのポインタが長さ 1 の配列の先頭要素を指すポインタと互換性を持つのは「加減算の二項演算の左右どちらかに表れるときに限って」とも解釈できます。

operators という語は字句的に二項演算子の +- に限定して言っているのか、それとも additive-expression に該当する全て (変数名一個として表れるときも含む) と解釈しても良いのでしょうか。

対象の規格

基本的には C++11 を想定していますが、後の変更で解釈が変わっているといったような補足事項があれば教えてくれるとありがたいです。

注意点

現実には上記のプログラムが期待通り動作しないなんてことはないだろうというのは承知しています。

あくまでも C++ の規格についての質問なので実際の処理系 (標準ライブラリ) がどのように動作するかを回答に含めないでください。

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

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

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

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

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

guest

回答3

0

ベストアンサー

C++17まではstring.cons#10

Requires: s points to an array of at least n elements of charT.

と最低n個の要素を持つ配列である事が求められていますが

C++20draftですと
constexpr basic_string(const charT* s, size_type n, const Allocator& a = Allocator());

constexpr basic_string(const charT* s, size_type n, const Allocator& a = Allocator());
Preconditions: [s, s + n) is a valid range.
Effects: Constructs an object whose initial value is the range [s, s + n).
Postconditions: size() is equal to n, and traits​::​compare(data(), s, n) is equal to 0.

sが配列へのポインタであることは求められていないように思います。

(というか、C++17以前だとsが配列先頭じゃないと駄目なんかな?
2次元配列の行を跨ぐ文字列とかダメそうな雰囲気が)

投稿2020/02/26 13:09

asm

総合スコア15149

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

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

0

非配列オブジェクトを指すポインタが配列の先頭を指すポインタと互換性を持つ条件が何かについては後で調査しますが、少なくともその例示は許可されません。なぜならnull文字終端が保証されないからです。

投稿2020/02/26 12:05

編集2020/02/26 12:05
yumetodo

総合スコア5852

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

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

0

一文字 (char) を文字列 (std::string) にするにあたってこのような書き方は言語仕様上は許されますか?

はい、問題ないかと思われます。

正式な仕様書を確認したわけではないのですが、stringのコンストラクタには、basic_string(const charT* s, size_type n, const Allocator& a = Allocator());という、単なるポインタを取るオーバーロードが含まれているとのことです(cpprefjp)。

「長さ 1 の配列の先頭要素を指すポインタ」とは、char (*ptr)[1];のように配列へのポインタとして宣言されたものを意味すると考えますので、この場面とは無関係かと思います。

投稿2020/02/26 02:17

maisumakun

総合スコア146018

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

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

SaitoAtsushi

2020/02/26 02:25

そのコンストラクタの説明にはこうあります。 Constructs an object of class basic_string and determines its initial string value from the array of charT of length n whose first element is designated by s, as indicated in Table 66. s は配列の先頭であるということが明示されており、非配列の変数を指すポインタを渡して良い根拠にはなりません。
guest

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

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

ただいまの回答率
85.35%

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

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

質問する

関連した質問