Screaming Loud

日々是精進

scalaからProcessを使って違うディレクトリでshを叩く

scalaでは他の言語でもできるように、コマンドを叩くことができます。

実際に色んな方が、Processの仕方を紹介をしています。
scala.sys.process | Scalaの標準ライブラリを使ってみる | mwSoft
Scala 2.9.0のscala.sys.processパッケージが便利過ぎる件について - kmizuの日記
scalaで外部コマンドを実行する - Qiita

詰まったところ

実行するjarファイルとは違うディレクトリのファイル操作を行いたかったのですが、cdコマンドがうまく動きませんでした。

解決方法

第2引数にjava.io.Fileのインスタンスを突っ込むとできました。

一つ目は正しく動く方法で、ふたつ目はうまく動かない方法です。

!マークは同期実行です。
非同期実行させたい場合は、!ではなくrunを利用しましょう。

The server quit without updating PID fileが発生して起動できない。

YosemiteからEICapitanにアップデートしたんですが、
その際にMySQLが起動できなくなったので、その解決法を共有します。

【環境】
MacOSX 10.11.2
$ mysql --version
mysql Ver 14.14 Distrib 5.6.26, for osx10.10 (x86_64) using EditLine wrapper
brewで入れたやつです)

事象

MySQLサーバを起動しようとすると以下のエラーが出て、起動出来ませんでした。

$ mysql.server restart
 ERROR! MySQL server PID file could not be found!
Starting MySQL
. ERROR! The server quit without updating PID file (/usr/local/var/mysql/{PC名}.pid).

解決策

mysqld_safeを打つだけ!

mysqld_safeを打つと、エラー発生時の再起動やエラーのロギングなど安全な起動が行われます。
MySQL :: MySQL 5.6 リファレンスマニュアル :: 4.3.2 mysqld_safe — MySQL サーバー起動スクリプト

$ mysqld_safe
160106 10:48:15 mysqld_safe Logging to '/var/log/mysql/error.log'.
touch: /var/log/mysql/error.log: No such file or directory
chmod: /var/log/mysql/error.log: No such file or directory
160106 10:48:15 mysqld_safe Starting mysqld daemon with databases from /usr/local/var/mysql
/usr/local/bin/mysqld_safe: line 129: /var/log/mysql/error.log: No such file or directory
/usr/local/bin/mysqld_safe: line 166: /var/log/mysql/error.log: No such file or directory
touch: /var/log/mysql/error.log: No such file or directory
chown: /var/log/mysql/error.log: No such file or directory
chmod: /var/log/mysql/error.log: No such file or directory
160106 10:48:15 mysqld_safe mysqld from pid file /usr/local/var/mysql

mysqlのログディレクトリが無い!と言われたので作ったら動きました。

原因

EICapitanに上げてから、/var/log以下がすっぽり亡くなってました。。
他のScalaから吐き出していたアプリケーションログもお亡くなりに。。

scala(breeze)で重回帰を実装

重回帰とは

重回帰は色んな所に転がっているので今更書かなくてもって感じですが、簡単に。


ある地域の住宅価格を求めたいとなった時に、ランダムで価格を当てるよりも何かの影響を受けて価格が変動すると考えるのが自然です。

 {住宅価格 = \beta_0 + \beta_1 *  犯罪率 + \beta_2 * 宅地の割合 + ...  \beta_n * 低所得者の割合 - (1)}

そこで上のような住宅価格は色んな要素に依存していると考え、各要素がどれくらい住宅価格を求めるのに影響があるのかを求めるのが重回帰です。

住宅価格に犯罪率の寄与が少なければ、{\beta_1}の値は小さくなるでしょうし、大きければその逆になります。

回帰を計算すると、各要素の係数であるβらが求まります。
βらが求まると、上記 (1) の式が埋まるので、新しいデータを各要素に当てはめると、そのデータに対する住宅価格が推定できるようになります。

この住宅価格を目的変数、犯罪率などの要素を説明変数と呼びます。

詳しくは、R - 重回帰モデルの理論と実装 -なぜ正則化が必要か- - Qiitaなどで式の導出は詳しく書かれています。
気になる方は、ぜひ導出も追ってみてください。

実装

Bostonの住宅の価格のCSVです。
Sense · Enterprise Data Science Platform

Python

上述のページで書かれているPythonコードの引用が以下になります。

import pandas as pd
import numpy as np
from numpy import linalg as la

df = pd.read_csv("Boston.csv", index_col=0)
y = df.iloc[:,  13].values
df = (df - df.mean())/df.std() # 基準化
X = df.iloc[:, :13].values
X = np.column_stack((np.ones(len(X)),X)) 
beta = np.dot(np.dot(la.inv(np.dot(X.T, X)),X.T), y)
print beta
R

Rのlm関数で書いたものの引用です

library(MASS)
X <- as.matrix(Boston[, -14])
y <- as.vector(Boston[,  14])
X <- scale(X) #基準化
model <- lm(y ~ X)
print(model)
scala

この式をScalaで書き直します。

def regression(file: File): DenseVector[Double] = {
  val mat = csvread(file, skipLines = 1)
  val y = mat(::, mat.cols - 1) // 目的変数
  val X = DenseMatrix.horzcat(
    DenseMatrix.tabulate(mat.rows, 1) { case _ => 1.0 }, // 要素がない列
    mat(::, 1 to mat.cols - 2) // 要素がある列
  ) // 説明変数の行列
  (inv(X.t * X) * X.t) * y
}

出力

DenseVector(36.45948838509085, -0.10801135783679613, 0.04642045836688007, 0.020558626367099816, 2.6867338193447603, -17.76661122830122, 3.809865206809127, 6.92224640347558E-4, -1.4755668456002482, 0.3060494789851876, -0.012334593916574491, -0.9527472317074077, 0.009311683273793751, -0.5247583778554944)
解説

上の式は

 {住宅価格 = \beta_0 + \beta_1 *  犯罪率 + \beta_2 * 宅地の割合 + ...  \beta_n * 低所得者の割合 - (1)}

Index,犯罪率,宅地の割合,...,低所得者の割合,住宅価格
1,0.5, 0.8, ... , 0.2, 5003,
2,0.53, 0.82, ... , 0.12, 600
3,...

のようなCSVを受け取ります。

まず、1行目で、CSVをロードして行列クラスにぶち込みます。

yは目的変数です。
上のcsvをそのまま行列に突っ込むと、最終列が住宅価格になるので、最終行を目的変数のベクトルとします。

Xは各要素群ですが、そのままだと{\beta_0}の列が作られません。
なので、tabulateで作成して、横で合成しています。
ここは見やすく、fillでVectorを作ってtoDenseMatrixでもよいです。

あとは、最小二乗法の解を求めるだけです。
{\beta = (X^TX)^{-1}X^Ty}
細かい導出式は、今回は求めませんので、他のサイトを見てみるとよいと思います。


今回は基準化を省いていますが、基準化を行うと各要素が同じスケールになるので、上の出力に出た係数を比較するだけでどの要素が目的変数に影響を及ぼすかがわかります。

ただその場合、係数のスケールが変わってしまっているので、目的変数の導出はスケールを戻さないと求められなくなります。


以下に動く実装を置いています。
regression/Regression.scala at master · moc-yuto/regression · GitHub

2015年を振り返る

昨日は読んだ本を振り返りましたが、全体を振り返ってみます。

今年は、Scalaを本格的に触った年でもあり、Angularを触った年でもありました。
また、トレーナーとしての経験も多く積みました。

1〜5月

前年からのプロジェクトを引き続き行っていました。
このプロジェクトは自らリーダーを降り、実装者として動くことを決意し、とにかくScalaを書きたいという思いからひたすらScalaを書いた期間でもありました。

バックエンドAPIサーバ、Webサーバののサーバサイド、ともにScalaだったので、そこをひたすら書いていました。
あと個人的にRailsを触ってフルスタックフレームワークの原点的なものを学べたのも良かったです。

外部LTで初めて発表したのもいい思い出でした。

6〜8月

やっとプロジェクトが落ち着き、トレンドであるDeepLearingを勉強したいなーと思い、勉強していたのもこの辺りです。
1〜5月にScalaを書きまくっていたので、やっと自信がついてきたのもこの当たりでした。

また、新卒が配属され、トレーナーとして動き始めたのも、自分の成長にかなり寄与していたと思います。
前年のプロジェクトでは、一度リーダーとしてチャンスを頂いたのですが、リーダーとしての動きが全くわからず、空回りをして色々迷惑をかけていたので、その挽回という意味でもトレーナーはいい経験でした。

また、スクラムマスターの勉強会に参加させてもらったこともチームの動き方を学べたいい経験でした。

9〜12月

新しいプロジェクトが始まり、リーダーとしての役割を任されるようになりました。
8月辺りでスクラムの勉強会に参加し、スクラムマスターとしてチームを回す経験を得られたことが良かったです。チームの人数が少ないため、スクラムマスターと開発者を兼任していたため、結構大変でした。兼任するとスクラムマスター業がおろそかになってしまうため、メンバーを全員スクラムマスターにしたいと思いました。

また、フロントがAngularJSだったので、AngularJSを触り始めたのもこの時期です。
今までJavaScriptフレームワークを触ったことがなかったので、一つの知見として増えたのはとても良かったです。

この時期、初めてWeb記事に寄稿の経験をしました。
寄稿の機会を作ってくださった先輩には感謝です。

さらに、トレーニーの人数が2人に増えどうなるか心配でしたが、なんとかやりきったかな―と思っています。
優秀なトレーニーで良かったです。

仕事以外

今年はvaingloryにハマった年でもありました。
まぁまだしばらくハマってしまいそうですが。。。

プライベートのほうは結構動きがありました。
前年はかなりゴタゴタがあったのですが、今年は落ち着く方向に動いて精神的にも良い方向に向かったので良かったです。

まとめ

アウトプットをもっとしていかなきゃなと感じています。
社会人としてもうすぐ4年目に突入してしまうので、もっとインプットとアウトプットのサイクルを早く回していかなければと。

あと、もうちょっと具体的な新年の抱負考えよーかな。
短いですが、この辺で。てへぺろ(・ω<)