RubyのNumericとTimeで数値と時間をさまざまな操作・演算・判定:若手エンジニア/初心者のためのRuby 2.1入門(6)(1/4 ページ)
オープンソースのオブジェクト指向プログラミング言語「Ruby」の文法を一から学ぶための入門連載。最新版の2.1に対応しています。今回は、数値/時刻を表現するクラスの使い方、型の変換、基本的な演算・比較、さまざまな用途で使える便利なメソッドなどを解説します。
組み込みクラスの最終回は、「数」に強くなる
前回の連載第5回記事「RubyのString/Regexpクラスによる強力な文字列操作/正規表現」では、Rubyを使ったテキスト処理に役立つ、文字列を表現するためのStringクラスと正規表現によるマッチングを行うためのRegexpクラスについて解説しました。
今回は、基本的なデータを表現する組み込みクラスの最終回ということで、数値を表現するためのNumericクラスと、時刻を表現するためのTimeクラスについて解説します。
数値を表現するためのNumericと、そのサブクラス
Numericクラスは、数値を表現するためのクラスです。これまで「1 + 1」のように何気なく数値演算してきましたが、これらの演算子(とはいえ実体はメソッドです)はNumericクラスと、それを継承する各数値型のクラスで定義されています。以下に数値クラスの継承関係を示します。
- Numeric(数値)
- Integer(整数)
- Fixnum(小さい整数)
- Bignum(大きい整数)
- Rational(有理数)
- Float(実数)
- Complex(複素数)
- Integer(整数)
整数を表現するInteger・Fixnum・Bignumクラス
先述の通り、整数は「Integer」という抽象的なクラスの下に、「Fixnum」「Bignum」という形で用意されています。Bignumの方が「Big」の名が示す通り、Fixnumでカバーできる数値の範囲を超えた場合に用いられます。classメソッドを使えばオブジェクトのクラスを確認できるので、pryを使って確かめてみましょう。
[1] pry(main)> 42.class => Fixnum [2] pry(main)> 1000000000000000000000000000000000000000000.class => Bignum
これらのクラスはちょっと特殊で、演算の結果がFixnumの範囲を超えると、Rubyの処理系が自動的にBignumに変換します。そのため、利用する側としてはその差をあまり意識することはないでしょう。
整数オブジェクトを生成するためには整数リテラルを使います。以下にさまざまな例を示します。
[3] pry(main)> 42 => 42 [4] pry(main)> -42 => -42 [5] pry(main)> 42_000_000 => 42000000 [6] pry(main)> 0b101010 => 42 [7] pry(main)> 052 => 42 [8] pry(main)> 0x2A => 42
[3]は最も基本的な表記で、10進数を用いて表現しています。[4]は42の前にハイフンを付けることで負の数を生成しています。また、[5]のようにアンダースコアを用いて桁を区切ると見やすくなります。
[6]〜[8]は10進数以外の形式で整数オブジェクトを生成しています。どれも10進数でいうところの42を生成していますが、[6]では0bというプレフィックスを使って2進数、[7]では0というプレフィックスを使って8進数、[8]では0xというプレフィックスを使って16進数で表記しています。
有理数を表現するRationalクラス
Rationalクラスは、有理数を表現するためのクラスです。有理数でピンとこない方は、分数を表すものだと理解してもよいでしょう。
実数を表現するクラスであるFloatがあれば十分ではないかと思わるかもしれませんが、Rationalは「1/3」(3分の1)のような、実数で表すと「0.333333……」のように循環小数になってしまう値を正確に表現できます。
- 2.1.0で追加された有理数リテラルを使う
Rationalオブジェクトを生成するためには、2.1.0で追加された有理数リテラルを使うのが便利です。いくつか例を示しましょう。
[1] pry(main)> 1/3r => (1/3) [2] pry(main)> 42r => (42/1) [3] pry(main)> 0.5r => (1/2)
[1]は一番素直な書き方で、「1/3」(3分の1)のような分数の形式で表記してRationalオブジェクトを生成しています。[2]はrの前に42のような整数の形式で表記してRationalオブジェクトを生成しています。
[3]は0.5のように小数の形式で表記してRationalオブジェクトを生成しています。返り値から、0.5の分数表記である「1/2」(2分の1)として扱われていることが分かります。
また、Rationalクラスのオブジェクトは常に既約、つまりそれ以上約分できない形となっています。ですので、以下の例のように「2/4r」「1/2r」は等しい数値として扱われます。
[4] pry(main)> 2/4r == 1/2r => true
- 2.1.0より前のバージョンの場合は、Rationalメソッドを使う
ここまで有理数リテラルを使う方法を紹介しましたが、2.1.0より前のバージョンではサポートされていません。そのため、2.1.0より前のバージョンを使っている現場では以下のようにKernelモジュールに定義されているRationalメソッドを使うやり方を見掛けることがあるでしょう。分子を第1引数に、分母を第2引数に与えます。
[5] pry(main)> Rational(1,3) => (1/3)
実数を表現するFloatクラス
Floatクラスは、実数を表現するためのクラスです。正確には浮動小数点数であり、その精度は実行環境に依存します。
整数のように、Floatオブジェクトも実数リテラルを使って生成するのが一般的です。以下にいくつか例を示します。
[1] pry(main)> 4.2 => 4.2 [2] pry(main)> 42e-1 => 4.2 [3] pry(main)> 0.42e+1 => 4.2
[1]が最も素直なパターンで、[2]および[3]は指数部と仮数部を使って表現しています。{仮数部}e{指数部}の形式で書き、{仮数部}の値の小数点を、右および左にいくつずらすかを{指数部}で指定します。
複素数を表現するComplexクラス
一般的なシステム開発ではなじみがないかもしれませんが、サイエンス色の強い分野では複素数を扱いたい場合もあるでしょう。Rubyには複素数を表現するComplexクラスがあります。
- 2.1.0で追加されたリテラルを使う
Rationalクラスと同様に、2.1.0から手軽にComplexオブジェクトを生成するためのリテラルが追加されました。以下にいくつか例を示しましょう。
[1] pry(main)> 42i => (0+42i) [2] pry(main)> 5 + 42i => (5+42i) [3] pry(main)> 42ri => (0+(42/1)*i)
[1]のように「42i」と書くと、虚部に42を持ち、実部に0を持つような数値となります。[2]のように整数と組み合わせて、実部を設定することもできます。[3]は有理数との合わせ技で、虚部に「42/1」という有理数を持つような複素数を生成することもできます。
- 2.1.0より前のバージョンの場合
以上のリテラル表記は2.1.0より前のバージョンではサポートされていないので、Rationalクラスと同様、以下のような表記を見掛けることも多いでしょう。
[4] pry(main)> Complex(5,42) => (5+42i)
Copyright © ITmedia, Inc. All Rights Reserved.