はじめに
C++をもう一度真面目に勉強するにあたりPythonで書いていたものをC++ではどう書くのかを中心に書いていく。そのため、この一連の記事はPythonは書けるけどC++は…という人向けに書いている(つもりである)。
内容としてはAtCoderのC++入門およびcpprefjp - C++日本語リファレンスをだいぶ参考にさせていただいている。
つたない内容であるがご容赦いただきたい。
代表的なデータ型
整数型
Pythonではこう書いた
Pythonで数値を扱う際にその表現範囲を気にすることはあまりないだろう。
i = 128
l = 2147483648
Python3.5で導入された型ヒントを用いることで静的言語っぽく書くこともできる。変数の定義時に使うことは多くないかもしれないが、思わぬミスを防ぐことはできる。型ヒント自体は後述する関数宣言時のほうが役に立つ印象。
i: int
i = 128 # i: int = 128 と1行でも書ける
C++ではこう書く
一方C++では整数型の表現範囲を考慮しないとオーバーフローで痛い目に合う。
int i = 128;
long l = 2147483648;
Python3系では型やその上限値を気にすることは(ほぼ)ないだろう(numpy
などを使う場合は別だが)。
※Python2系ではint
とlong
が存在した。
浮動小数点型
Pythonではこう書いた
f = 0.001
d = 0.001
整数値でも0.0
などとすればfloat
として扱われる。型ヒントも使えるが、代入する値の型が優先される模様。
f: float
f = 1. # f: float = 1. と1行でも書ける
# f: float = 1 # こう書くとfはintになってしまう
C++ではこう書く
float f = 0.3;
double d;
d = 1.2345;
Pythonのfloat
はC++だとdouble
相当(倍精度)とのこと。
文字 / 文字列
Python2系では文字列としてunicode
とstr
の2種類が存在しており非常にややこしかったが、Python3系では文字列は一律str
で扱われるようになりシンプルになった。
Pythonではこう書いた
moji = "hello"
print(moji) # hello が出力される
print(len(moji)) # 文字数である 5 が出力される
letter = "H" # pythonでは文字列/文字に差はない
#moji[0] = letter # このような置換はできない
moji = moji.replace(moji[0], letter) # replaceメソッドを使う必要がある
print(moji) # Hello が出力される
print(len("Hello")) # 5(文字列をそのまま使える)
print(moji + moji) # HelloHello が出力される(string同士は+演算子で連結可)
C++ではこう書く
Pythonでは文字数によらずstr
として扱われるが、C++では文字数によってchar
またはstring
として扱われる。また、Pythonでは文字列を囲む"
と'
の違いを意識することはほぼないと思われるが、C++では'
はchar
を、"
はstring
に対して使われると考える。
string moji = "hello";
cout << moji << endl; // hello が出力される
cout << moji.size() << endl; // 5 が出力される
char letter = 'H'; // char型は一文字のみ
moji.at(0) = letter; // C++ではこのような置換が可能
cout << moji << endl; // Hello が出力される
cout << "Hello"s.size() << endl; // 5(文字列をそのまま使う場合、末尾にsをつける必要あり)
cout << moji + moji << endl; // HelloHello が出力される(string同士は+演算子で連結可)
cout << moji + letter << endl; // HelloH が出力される(stringとcharも+演算子で連結可)
まとめ
C++ | Python | |
---|---|---|
宣言 / 定義 | string word = "文字列"; | word = "文字列" |
任意要素へのアクセス(1) 1 | word.at(i); 2 | word[i] 3 |
任意要素へのアクセス(2) 4 | word[i]; 2 | 同上 |
先頭要素へのアクセス | word.front(); | word[0] |
末尾要素へのアクセス | word.back(); | word[-1] |
末尾要素の削除 | word.pop_back(); | word = word[:-1] |
文字列の長さを取得(1) | word.size(); | len(word) |
文字列の長さを取得(2) | word.length(); | 同上 |
文字/文字列を追加(1) | word.append(string2); | word += string2 |
文字/文字列を追加(2) | word += string2; | 同上 |
末尾に文字を追加 5 | word.push_back(character); | word += character |
文字列の一部を置換 6 | word.replace(index1, index2, string2); | word.replace("置換前文字列", "置換後文字列") |
指定文字列を検索 7 | word.find(string2); | word.find(string2) |
指定文字列を末尾から検索 | word.rfind(string2); | word.rfind(string2) |
文字列が空かどうかを判定 | word.empty(); | len(word) == 0 |
文字列をクリア | word.clear(); | word = "" |
指定の文字列で始まるかを判定する | word.starts_with(string2); 8 | word.startswith(string2) |
指定の文字列で終わるかを判定する | word.ends_with(string2); 9 | word.endswith(string2) |
指定の文字・文字列が含まれているかを判定する | word.contains(string2); 10 | string2 in word |
autoによる型推論
C++において、変数の型を初期化子から推論することができる。これにより型を(ある程度)気にせずに変数宣言ができる。Pythonで変数を定義するのとほぼ同じ感覚で変数を用意できる。
Pythonではこう書いた
a = 120 # intになる
f = 0.001 # floatになる
C++ではこう書く
初期化を伴う変数宣言の場合は、auto
で変数の型を省略できる。
auto a = 120; // intになる
auto d = 0.001; // doubleになる