https://youtu.be/kEpTfxvXNE0
今回はThe Basics
の 整数リテラル
について見ていきます。前回の型推論の話の中で出てきたリテラルについて、もう少しだけ紹介していく節になる様子ですけれど、せっかくなので整数リテラル周りのおさらいを思い当たる限りでしていけたらいいなと思ってます。よろしくお願いしますね。
———————————————————————————— 熊谷さんのやさしい Swift 勉強会 #116
00:00 開始 00:39 整数リテラル 03:09 8進数リテラル 11:29 2進数リテラル 12:28 C++ 日本語リファレンス cpprefjp 13:52 16進数浮動小数点数リテラル 15:17 C 言語での2進数的表現 18:18 C 言語における8進数リテラル表記の事情 19:16 8進数と Linux のパーミッション 26:13 8進数リテラルの使いどころは? 28:02 次回の展望 ————————————————————————————
Transcription & Summarize : 熊谷さんのやさしい Swift 勉強会 #116
今日は数値リテラル、特に整数リテラルについてお話しします。前回の型推論とリテラルを組み合わせた話の続きとして、このセクションに入る感じです。今回もその部分をもう少し細かく解説していきます。
まずは整数リテラルから見ていくことになります。Swiftのリテラルは、Objective-CやC言語と比べて非常に細かく設定されています。十進数はもちろんのこと、画面に表示されているように二進数、八進数、十六進数もリテラルで表現できるのが特徴的です。
C言語でも最近、C++11からこれらのリテラル表現が取り入れられています。C++11は2011年に仕様が策定され、その後2年間で実装されました。Appleが採用しているClang(クラング)の実装も早く、ほぼ2011年ぐらいにはC++11の仕様を取り込んでいました。それにより、二進数リテラルがC++で使えるようになったのです。
Swiftでも二進数リテラルが書けるようになったのは、とても嬉しい仕様ですね。ただ、Swiftは約10年前から存在しており、C++11も10年以上前のものなので、二進数リテラルが特別といった印象は薄れています。それでも、Swiftがこうしたリテラル表現を柔軟にサポートするのは便利です。
ちなみに、PHPやC言語では、先頭がゼロから始まる数値は八進数表現となるので注意が必要です。Objective-Cでも同様で、ゼロから始めてしまうと八進数として認識されてしまうため、意図せず異なる数値が扱われることがあります。
ここで、Objective-Cのインタフェースに関するコードを例として紹介します。例としてint
型のナンバーを100と設定すると、
int number = 100;
のように書くことができます。ただし、古い記述方法やプロパティなども絡んでくるため、少々混乱しやすい部分もあります。正確に書いておかないと、コンパイルエラーが出ることもあります。
最後に、具体的なコードの実装部分については、適切にインタフェースやプロパティを設定し、必要なタイミングで適用することが重要です。具体的なコード例を試しながら学習することで、理解が深まるはずです。 オブジェクティブ性のコードについては、将来的にはオブジェクティブ性を習得する人々が増えてくるかもしれませんね。例えば、msインテジャーでnumber
としてここでリターンするとき、問題なく値を返すことができます。また、プロパティももっと簡単に取得できるでしょう。
というわけで、ビルドが通っていれば、メイン関数の中でlet object = SomeObject()
(インスタンス化されているオブジェクト)を使うことができます。そして、Objective-C bridge
をインポートしてからビルドを実行します。これで、print(object.number)
を実行すると、正しく値が表示されるはずです。例えば、100と出るはずですが、それが確認できます。
次に、C言語でもよくある誤りですが、属性を使って正確に表示する方法について話します。例えばプロパティint
を持つオブジェクトがあって、それが100という値を持つとします。同様に他の値も設定した場合、桁合わせに苦労することがあります。例えば、let number = 0100
と書くと、これは実際には8進数として認識され、結果として64となってしまいます。しかし、Swiftではそのような誤解が生じないように、0Bを用いて2進数、0Oを用いて8進数、0xを用いて16進数として明示的に指定することができます。
let number = 0O100
と書けば、これは8進数として正しく解釈され、結果として64となります。これは、他のプログラミング言語では混乱しがちな部分を解決してくれるので、とても便利です。
次に、C++14からは二進数リテラルがサポートされ始めました。サポートするには、0b
または0B
を用います。これにより、二進数リテラルも簡単に扱うことができるようになります。C++の標準仕様を確認すると、確かに0b
と0B
が使われているのがわかります。
このように、様々なプログラミング言語でリテラルの扱いが進化しており、その使用例としてSwiftでも同様の表記がサポートされています。Swiftのリテラル表記はとても便利で、安全にコードを書くための助けとなります。 リテラル表記について話していると、Swiftではリテラルの書き方がより自然になっており、統一感のある書き方ができると説明しています。具体例として、10進数、16進数 (0x
)、8進数 (0o
)、2進数 (0b
) の表記が挙げられます。たとえば、0x
で始まるものは16進数リテラル、0o
なら8進数リテラル、0b
なら2進数リテラルです。
コメントをいただいた内容から、C言語でのビット操作の例として、1を3回左シフトする方法も紹介されます。ビット操作はフラグ管理によく使われる手法であり、たとえば、1を3回シフトしたもの
と 1を1回シフトしたもの
を足すことで3ビット目と1ビット目が1の値を作るといった方法です。これは、特定のキーが押されたときのフラグ設定などに活用されます。
さらに、Swiftの2進数リテラルの利便性についても触れており、例えば 0b01
や 0b10
といった2進数リテラルを使うことでコードがわかりやすくなることを強調しています。特に桁を揃えることで、可読性が向上します。
また、歴史的な事情でC言語では 0
を付けると8進数リテラルになるという話題も出ています。その理由については詳しくはわからないものの、UNIXシステムでのパーミッション設定と関連があるのではないかと推測しています。例えば、chmod 755
のような8進数表記が使われています。chmod
コマンドで 0755
といったように8進数表記が使われることにも関連しているのかもしれません。ただ、この推測には確証がないため、詳細は調査が必要です。
最後に、Linuxのパーミッション設定に関しても言及されています。たとえば、chmod 1755
のように4桁目に特定のビット (TTビット
) を設定することで、特定の権限を追加できることが説明されます。これはWebサーバーのCGIスクリプトの設定などで重要な部分です。 とりあえず、これが8進数なんですよ。フラグだから8進数と合っているわけです。要は同じ間隔でフラグを用意していくのですが、たとえばリードを0ビット目、ライトを2ビット目、実行を3ビット目とすると、ちょうど4ビットで8進数に対応します。リードが 0B001
、ライトが 0B010
、実行が 0B100
になります。
フラグを設定するとき、リードとライト、実行などいろんなパターンを試したいので、たとえば P1
はすべてのフラグをセットし、P2
はリードと実行、P3
はリードだけといった感じにできます。これで実行すると 0755
のような値になります。
これをユーザー、グループ、その他に分けて考えると、たとえばユーザーはリード、ライト、実行のすべてを許可し、グループとその他はリードと実行を許可する場合、0755
になります。これはユーザーに対してビットシフトを適用したものです。具体的には、ユーザーのフラグは rwx
で、グループとその他は rx
になります。
このようにフラグを指定する際に、C言語などでは8進数表記を使います。これは頭に 0
をつけることで表現します。たとえば、0755
という形です。しかし注意が必要です。8進数と10進数の違いで、バグが発生しやすいためです。
私自身も以前、スキュリティビットを設定しようとして、頭に 0
をつけずに書いてしまい、10進数として扱われてしまって問題が発生しました。このような仕様については注意が必要です。
8進数や16進数表記のリテラルを適切に使用すると、コードの読みやすさやメンテナンスが向上します。特に、昔からプログラミングをしている人にとっては、8進数表記や16進数表記は馴染みが深いでしょう。
次回は、不動小数点数のリテラルについて詳しく触れる予定です。今回いくつかのリテラルについて紹介しましたが、時間の関係で詳細な説明は次回に回します。
今日はこれで終わりにします。お疲れさまでした。ありがとうございました。