多くの企業でビッグデータを解析することが当たり前になってきている近年、ビジネスにおいても統計解析が不可欠です。そこで、統計解析分野のプログラミング言語として注目されているのが「R(R言語)」。グラフ作成に優れているなど、解析に便利な機能が搭載されており、記述もシンプルということからPythonと並んで非常によく使われています。
以前の記事では、R言語のインストール方法とワークフローを解説いたしましたので、今回は構文の作り方を解説いたします。
演算子のルール、データ構造、Data frame、変数など、基本的な部分を網羅しましたので、「これから勉強しようと思っていた」という方はぜひこの記事で学んでみてください。
目次
1.演算子
プログラミング言語では、「演算子」によってどのような操作をしているかを示します。
演算子は論理的/数学的操作をコンピュータに伝える役目をしています。Rには豊富な演算子が用意されています。
演算子は様々な形をしており、それぞれに別々の機能が携わっています。データ操作においては、モデルの公式やリストのインデクシングのような少し発展的な演算子も存在します。
モデルの公式は、統計的手法や、機械学習手法を扱う上で必ず必要になってきます。しかし、覚えてしまえば簡単に扱うことができるのでしっかりとものにするようにしましょう。
また、「インデクシング」とはインデックスの操作のことです。インデックスとはリストやベクトル、行列の位置番号を表します。Rのインデックスは1から始まります。また、行番号であれば上から、列番号であれば左から始まります。インデクシングもデータを扱う上で必須の知識になります。それは、統計的手法や機械学習において、ベクトルや行列が必須になるからです。それでは早速代入演算子から見ていきましょう。
1-1.代入演算子
No. | 演算子 | 説明 |
1 | <- or = | 左に代入 |
2 | -> | 右に代入 |
代入演算子は変数にあらたな値を代入するときに使用します。Rでは、代入演算子をベクトルの代入の時に使用します。
例:
# 左に代入
a <- 1:10
b = letters[1:10]
print(a)
[1] 1 2 3 4 5 6 7 8 9 10
print(b)
[1] "a" "b" "c" "d" "e" "f" "g" "h" "i" "j"
# 右に代入
3 -> a
print(a)
[1] 3
ここで、右に代入の時に、前回使用したaという変数に代入しています。この時Rでは新しく代入した値が優先されることに注意しましょう。
また、変数の名前を考えるときには被らないような名前を付けるようにしましょう。
1-2.算術演算子
No. | 演算子 | 説明 |
1 | + | 足し算 |
2 | – | 引き算 |
3 | * | 掛け算 |
4 | / | 割り算 |
5 | ^ or ** | 指数演算 |
こちらの演算子は普段から見慣れたものが並んでいます。掛け算と割り算、指数演算だけ注意しましょう。
例:
# 足し算
# 数
1 + 1
[1] 2
# ベクトル
a <- 1:5
b <- 6:10
c <- a + b
print(c)
[1] 7 9 11 13 15
# 引き算
c <- b-a
print(c)
[1] 5 5 5 5 5
# 掛け算
c <- a*b
print(c)
[1] 6 14 24 36 50
# 割り算
c <- b/a
print(c)
[1] 6.000000 3.500000 2.666667 2.250000 2.000000
# 指数演算
c <- a^b
print(c)
[1] 1 128 6561 262144 9765625
1-3.関係演算子
No | 演算子 | 説明 |
1 | > | 大なり |
2 | < | 小なり |
3 | >= | 大なりイコール |
4 | <= | 小なりイコール |
5 | == | イコール |
6 | != | ノットイコール |
関係演算子は2つの変数間の関係をTRUEかFALSEで評価する演算子です。
例えば、5>3は正解なのでTRUEを返します。5<3は間違っているのでFALSEを返します。イコールのときに==と等記号を2つ繋げるところに注意してください。
1つだけですと代入という意味になってしまうのでしたね。また、TRUEとFALSEの2つを論理型(Logical)変数といいます。この変数はBoolean(ブーリアン)ともいい、ほかのプログラミング言語でも必ず出てくるもので、これを駆使することでデータ操作を行います。
例:
a <- 1:5
b <- 5:1
a>b
[1] FALSE FALSE FALSE TRUE TRUE
a=b
[1] FALSE FALSE TRUE TRUE TRUE
a<=b
[1] TRUE TRUE TRUE FALSE FALSE
a==b
[1] FALSE FALSE TRUE FALSE FALSE
a!=b
[1] TRUE TRUE FALSE TRUE TRUE
1-4.論理演算子
No. | 演算子 | 説明 |
1 | & | かつ |
2 | | | または |
3 | ! | 否定 |
4 | && | かつ(1番目の値のみ) |
5 | || | または(1番目の値のみ) |
論理演算子は〇〇かつ△△や、○○または△△などの場合のLogicalを返します。つまり複数の条件に基づいてLogicalを返すということですね。
例:
# 0, 1のセットが5つ並んだベクトル
a <- rep(c(0,1), 5)
# 1が10個並んだベクトル
b <- rep(1, 10)
# aとbの値が1の時(a AND b)TRUEを返す
a&b
[1] FALSE TRUE FALSE TRUE FALSE TRUE FALSE TRUE FALSE TRUE
# aかbの値が1の時(a OR b)FALSEを返す(bが全部1なのですべてTRUE)
a|b
[1] TRUE TRUE TRUE TRUE TRUE TRUE TRUE TRUE TRUE TRUE
# 0は数値型だがLogicalではFALSE扱いとなる
# 否定なので0がTRUE、1がFALSEになる
!a
[1] TRUE FALSE TRUE FALSE TRUE FALSE TRUE FALSE TRUE FALSE
!b
[1] FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE FALSE
# aとbの最初の値を比較する(a AND b)
a&&b
[1] FALSE
# aとbの最初の値を比較する(a AND b)
a||b
[1] TRUE
1-5.その他の演算子
No. | 演算子 | 説明 |
1 | : | 連続する数値を出力 |
2 | %in% | 左のベクトルの値が右ベクトルに含まれているか |
3 | %*% | 行列の掛け算 |
これまで紹介してきた演算子以外の演算子は、特別な状況でのみ使用します。それらの演算子は一般的な数学や理論では用いないものです。
例:
#colon operator ":"
a <- 1:5
# %in%
b <- 3:10
a%in%b
[1] FALSE FALSE TRUE TRUE TRUE
# %*%
m1 <- matrix(1:10, nrow = 2, ncol = 5)
m2 <- matrix(1:5, nrow = 5, ncol = 1)
m <- m1%*%m2
print(m)
[,1]
[1,] 95
[2,] 110
2.Rのデータ型
以下が、変数の値に入るデータ型です。プログラミング言語では、様々な情報を貯蓄するために変数を用います。
型 | 例 | 説明 |
Logical | TRUE, FALSE, NA | 論理値 |
Numeric | 1.33333, 1234.3 | 実数 |
Integer | 1, 23, 10000 | 整数 |
Complex | 100+2i, 42i | 複素数 |
Character | ‘hello’, ‘14.5’, ‘TRUE’ | 文字列 |
例:
a <- 1:5
b <- 3:7
c <- a%in%b
d <- c(1, 2, "one", "two", "TRUE")
e <- 300i
3.Rのオブジェクトであるデータ構造
オブジェクトとはRの中で使用するものすべての呼称です。データ構造はコンピュータサイエンスの場では別の意味で用いられますが、この記事ではデータ構造をすべてRのオブジェクトのこととします。
データ構造を理解することは非常に重要です。データ構造はRで毎日操作するものになります。また、初学者にとってデータ構造の操作はかなり苦戦するかと思われますので、何度も復習してマスターすることを心がけましょう。
Rのデータ構造
- Atomic vector
- List
- Array
- Matrices
- Data Frame
- Factors
3.1.Atomic vector
ベクトルはRのデータ構造の中で基本の位置づけになります。ベクトルは、数値、文字列、理論値の要素が1行(列)に集まったものです。
例:
# ベクトルの作成
a <- 1:10
b <- letters[1:10]
# ベクトル型であるかチェックする
is.vector(a)
[1] TRUE
is.vector(b)
[1] TRUE
3.2.List
リストはベクトルと非常に似ていますが、リストのほうが汎用性が高いという特徴があります。リストを構成する要素には任意のものが当てはまるため、中には、異なるデータ型の要素が入ってることもあります。
例:
# リストの作成
a <- 1:10
b <- letters[1:10]
c <- list(a=a, b=b)
str(c)
List of 2
$ a: int [1:10] 1 2 3 4 5 6 7 8 9 10
$ b: chr [1:10] "a" "b" "c" "d" ...
# 型のチェック
class(c)
[1] "list"
# list()の代わりにc()を使用してみる
d <- c(a, b)
# 新たなベクトルが得られる
print(d)
[1] "1" "2" "3" "4" "5" "6" "7" "8" "9" "10" "a" "b" "c" "d" "e"
[16] "f" "g" "h" "i" "j"
# 型のチェック
class(d)
[1] "character"
3.3.Matrices(行列)
行列は2次元以上の要素の集まりです。長さが同じベクトルが2つ以上合体したオブジェクトです。行列では、要素に常に数値データが入ります。これは行列演算を行うためです。行列を作成するにはmatrix()関数を使用します。
例:
# 行列を作成
m1 <- matrix(1:10, nrow = 2, ncol = 5)
m1
[,1] [,2] [,3] [,4] [,5]
[1,] 1 3 5 7 9
[2,] 2 4 6 8 10
m2 <- matrix(1:5, nrow = 5, ncol = 1)
m2
[,1]
[1,] 1
[2,] 2
[3,] 3
[4,] 4
[5,] 5
m12 <- m1%*%m2
print(m12)
[,1]
[1,] 95
[2,] 110
# 次元に名前を付ける
m3 <- matrix(1:30, ncol = 7, byrow = T)
Warning in matrix(1:30, ncol = 7, byrow = T): data length [30] is not a sub-
multiple or multiple of the number of columns [7]
m3
[,1] [,2] [,3] [,4] [,5] [,6] [,7]
[1,] 1 2 3 4 5 6 7
[2,] 8 9 10 11 12 13 14
[3,] 15 16 17 18 19 20 21
[4,] 22 23 24 25 26 27 28
[5,] 29 30 1 2 3 4 5
dimnames(m3) <- list(paste0("Week", 1:5),
c("Monday", "Tuesday", "Wednesday", "Thursday", "Friday",
"Saturday", "Sunday")
)
m3
Monday Tuesday Wednesday Thursday Friday Saturday Sunday
Week1 1 2 3 4 5 6 7
Week2 8 9 10 11 12 13 14
Week3 15 16 17 18 19 20 21
Week4 22 23 24 25 26 27 28
Week5 29 30 1 2 3 4 5
# 特定の行、列の値を抽出する
m3[1,2] #row 1, column2 of m3
[1] 2
m3[,3] # column 3 of m3
Week1 Week2 Week3 Week4 Week5
3 10 17 24 1
m3[4,] #row 4 of m3
Monday Tuesday Wednesday Thursday Friday Saturday Sunday
22 23 24 25 26 27 28
3.4.Arrays(配列)
Array型は2つ以上のmatrixをもつデータ構造です。例えば、1つのmatrixを2つに分解したいというときにはこのarrayにデータを変換することができます。以下の例は、長さ10のベクトルa, 長さ20のベクトルbを作成し、この2つのベクトルを組み合わせた5行6列の行列を2つ作ります。そして、2つの行列をarrayに保存することで、5行6列の行列を2つ((5, 6, 2)と表記する)もったarray型のデータを作成しています。
例:
# ベクトルa, bの作成
a <- 1:10
b <- letters[1:20]
# 2つのベクトルを1つのarrayに保存する
array1 <- array(c(a, b), dim=c(5,6,2))
print(array1)
, , 1
[,1] [,2] [,3] [,4] [,5] [,6]
[1,] "1" "6" "a" "f" "k" "p"
[2,] "2" "7" "b" "g" "l" "q"
[3,] "3" "8" "c" "h" "m" "r"
[4,] "4" "9" "d" "i" "n" "s"
[5,] "5" "10" "e" "j" "o" "t"
, , 2
[,1] [,2] [,3] [,4] [,5] [,6]
[1,] "1" "6" "a" "f" "k" "p"
[2,] "2" "7" "b" "g" "l" "q"
[3,] "3" "8" "c" "h" "m" "r"
[4,] "4" "9" "d" "i" "n" "s"
[5,] "5" "10" "e" "j" "o" "t"
# arrayのデータを抽出するには[]を使用します
array1[3,2,1] # row 3, column 2, matrix 1
[1] "8"
array1[,2,1] # all the column2 matrix 1
[1] "6" "7" "8" "9" "10"
array1[,,2] # all the matrix 2
[,1] [,2] [,3] [,4] [,5] [,6]
[1,] "1" "6" "a" "f" "k" "p"
[2,] "2" "7" "b" "g" "l" "q"
[3,] "3" "8" "c" "h" "m" "r"
[4,] "4" "9" "d" "i" "n" "s"
[5,] "5" "10" "e" "j" "o" "t"
3.5.Data frame
Data frameはテーブルのようなもので、構造としてはarrayに似た特徴を持っています。行のことをindexまたはrowと呼び、列のことをcolumnと呼びます。
Data frameの特徴
- columnには必ず名前が必要
- rowの名前はユニークであることが必要
- データフレームにあるデータは数値や文字列など任意のものが可能
- それぞれのcolumnには同じ数のデータが入っている
例:
# Create a dataframe
a <- 1:10
b <- letters[1:10]
df1 <- data.frame(No=a, Letters=b)
df1
No Letters
1 1 a
2 2 b
3 3 c
4 4 d
5 5 e
6 6 f
7 7 g
8 8 h
9 9 i
10 10 j
3.6.Factors
factorはデータをカテゴリに分けて保存するデータ構造です。数値と文字の両方をデータの要素として持つことができます。data frameのcolumnの名前を付けるときなどに利用すると便利に働きます。
例:
# 文字のベクトルを生成
b <- rep(letters[1:10], 10)
b
[1] "a" "b" "c" "d" "e" "f" "g" "h" "i" "j" "a" "b" "c" "d" "e" "f" "g" "h"
[19] "i" "j" "a" "b" "c" "d" "e" "f" "g" "h" "i" "j" "a" "b" "c" "d" "e" "f"
[37] "g" "h" "i" "j" "a" "b" "c" "d" "e" "f" "g" "h" "i" "j" "a" "b" "c" "d"
[55] "e" "f" "g" "h" "i" "j" "a" "b" "c" "d" "e" "f" "g" "h" "i" "j" "a" "b"
[73] "c" "d" "e" "f" "g" "h" "i" "j" "a" "b" "c" "d" "e" "f" "g" "h" "i" "j"
[91] "a" "b" "c" "d" "e" "f" "g" "h" "i" "j"
# ラベルをレベルを引数に持たせfactorを生成
ft <- factor(b,
labels = LETTERS[1:10],
levels = letters[1:10]
)
ft
[1] A B C D E F G H I J A B C D E F G H I J A B C D E F G H I J A B C D E F G
[38] H I J A B C D E F G H I J A B C D E F G H I J A B C D E F G H I J A B C D
[75] E F G H I J A B C D E F G H I J A B C D E F G H I J
Levels: A B C D E F G H I J
4.Rの変数
変数はプログラミングにおいて、あらゆる情報を保持し、それらの操作を可能にするとても重要な要素です。Rの変数はこれまで紹介してきたデータ構造を保存することができる特徴があります。
変数を扱う上でとても重要なのが、変数の命名です。プログラミングのコードは自分が見るよりも、他人に見てもらうことのほうが多いです。その時に、変数の名前をaとかbなどにしておくと、これらの変数が一体どんな情報を保持しているかがわからなくなってしまいます。
また、命名にはいくつかのルールが存在しています。以下の表を参考にしてください。
No | Names | Validity | Explanation |
1 | var_name | 可 | _(アンダースコア)で名前をつなげることができます |
2 | var.name | 可 | .(ドット)で名前をつなげることができます |
3 | var_name2 | 可 | 数字は文字の後に置くことができます |
4 | .varname | 可 | .(ドット)は名前の最初においても無視されます |
5 | _var_name | 不可 | 名前の最初に_(アンダースコア)は使えません |
6 | var.name% | 不可 | .(ドット)と_(アンダースコア)以外の特殊文字は使えません |
7 | 2.varname | 不可 | 名前の最初に数字は使えません |
8 | .3varname | 不可 | 同上 |
9 | var name 23 | 不可 | スペースは使えません |
5.制御構文
プログラムを作成するうえで制御構文は必ず使用します。制御構文とは条件によってプログラムを動かすか判断したり、繰り返しプログラムを実行したいときなどに使用します。これらを駆使して複雑な動きを実装することができます。
5.1.if, else文
まずは条件分岐からです。条件分岐とはある条件がTRUEの場合に実行し、FALSEの場合は無視する働きをするものです。Rではifとelseを使用します。
# if文の例です
if (条件) {
処理
}
”条件”がTRUEのときに”処理”が行われます。また、{}ないの分は必ずインデントしましょう(tabキーを押す)。インデントすることでコードが読みやすくなります。
# ifとelseの組み合わせの例です
if (条件) {
処理1
} else {
処理2
}
elseはifの条件がFALSEのときに処理したいものがある場合に使用します。上の例では”条件”がTRUEの時に”処理1”が実行され、FALSEの時に”処理2”が実行されます。
例:
# ifとelseを組み合わせて条件分岐
a = 1
b = 10
if (a == b) {
a = a - b
} else {
a = a + b
}
a
[1] 11
5.2.for, while文
続いて繰り返し処理です。for文もしくはwhile文を使用します。for文はデータの中身一個一個に処理を行うときに使用します。while文は条件がTRUEの間繰り返し処理を行います。
# for文の例
for (変数 in データ構造) {
処理
}
for文ではデータ構造の中のデータが1個ずつ変数に入り、データ構造の中身がなくなるまで繰り返し処理を行います。中身がなくなれば次のプログラムに自動的に移ります。
例:
# for文でdrinkの中身を1個ずつ表示する
drink = c("beer", "juice", "tea", "coffee")
for (name in drink) {
print(name)
}
[1] "beer"
[1] "juice"
[1] "tea"
[1] "coffee"
次にwhile文の例を示します。
# while文の例
while (条件) {
処理
}
実際にコードにしてみましょう。
# nが100になるまで1ずつ足していく
n = 0
while (n < 100) {
n = n + 1
}
n
[1] 100
上の例ではnが100になるまでnに1ずつ足しています。その結果nは100となっていることがわかります。99ではないのかと思うかもしれませんが、nが100になったときにwhile文から抜け出すので、nは100となります。
6.まとめ
この記事では基礎的な構文を復習しましたが、一通り身につけられた後は以下のggplot2に挑戦するのももおすすめです。
コメント