Ubuntu で XGBoost4J のビルド & 実行


# 事前準備
- 以下をインストール
 - Java 1.7 or later
 - Git
 - g++
 - Maven
- 環境変数 JAVA_HOME を設定

# XGBoost4Jのビルド
```
$ git clone --recursive https://github.com/dmlc/xgboost
$ cd xgboost/jvm-packages
$ mvn package install
```

# データ形式
XGBoost4J では LIBSVM形式のファイル、CSR/CSC形式の疎行列、密行列を取り扱える。LIBSVM形式のデータセットは以下から取得できる。
- [LIBSVM Data: Classification, Regression, and Multi-label](https://www.csie.ntu.edu.tw/~cjlin/libsvmtools/datasets/)

分類問題において、ラベルは 0～クラス数-1 （2値分類では0,1、3値分類では0,1,2）でなければならないので上記のデータセットを使用する場合は修正が必要。


# 実行例その1 - 分類 & cross validation

[ここ](https://www.csie.ntu.edu.tw/~cjlin/libsvmtools/datasets/multiclass.html#iris)から iris データをダウンロード。
ラベルが 1, 2, 3 となっているので 0, 1, 2 に修正する。

```groovy:build.gradle
repositories {
    mavenLocal()
}

dependencies {
    compile 'ml.dmlc:xgboost4j:0.5'
}
```


```java:XGBoost4JClassificationTest.java
import java.util.HashMap;
import java.util.Map;

import ml.dmlc.xgboost4j.java.DMatrix;
import ml.dmlc.xgboost4j.java.XGBoost;
import ml.dmlc.xgboost4j.java.XGBoostError;

public class XGBoost4JClassificationTest {

	private static final String trainMatPath = "data/iris.scale";

	public static void main(String[] args) throws XGBoostError {
		DMatrix trainMat = new DMatrix(trainMatPath);

		Map<String, Object> params = new HashMap<>();
		params.put("objective", "multi:softmax");
		params.put("num_class", 3);     // 多値分類の場合は "num_class" でクラス数を指定

		int round = 10;
		int nfold = 5;	// 5-fold
        // cross validation
		String[] evalHists = XGBoost.crossValidation(trainMat, params, round, nfold, null, null, null);  
		for (String evalHist : evalHists) {
			System.out.println(evalHist);
		}
	}
}
```


```txt:結果
[0]	cv-test-merror:0.066667	cv-train-merror:0.023333
[1]	cv-test-merror:0.066667	cv-train-merror:0.023333
[2]	cv-test-merror:0.053333	cv-train-merror:0.020000
[3]	cv-test-merror:0.060000	cv-train-merror:0.018333
[4]	cv-test-merror:0.053333	cv-train-merror:0.016667
[5]	cv-test-merror:0.053333	cv-train-merror:0.015000
[6]	cv-test-merror:0.053333	cv-train-merror:0.015000
[7]	cv-test-merror:0.046667	cv-train-merror:0.011667
[8]	cv-test-merror:0.046667	cv-train-merror:0.010000
[9]	cv-test-merror:0.046667	cv-train-merror:0.010000
```

- XGBoost.crossValidation() で cross validation を行う
- 分類では error rate、回帰では RMSE が出力される


# 実行例その2 - 回帰 & 学習、予測データを指定
[ここ](https://www.csie.ntu.edu.tw/~cjlin/libsvmtools/datasets/regression.html#housing)から housing データをダウンロード。
学習用と予測用に分割する。

```java:XGBoost4JRegressionTest.java
import java.util.HashMap;
import java.util.Map;

import ml.dmlc.xgboost4j.java.Booster;
import ml.dmlc.xgboost4j.java.DMatrix;
import ml.dmlc.xgboost4j.java.XGBoost;
import ml.dmlc.xgboost4j.java.XGBoostError;

public class XGBoost4JRegressionTest {

	private static final String trainMatPath = "data/housing.scale.train";
	private static final String testMatPath = "data/housing.scale.test";

	public static void main(String[] args) throws XGBoostError {
		DMatrix trainMat = new DMatrix(trainMatPath);
		DMatrix testMat = new DMatrix(testMatPath);
        
		Map<String, Object> params = new HashMap<>();
		params.put("objective", "reg:linear");

		Map<String, DMatrix> watches = new HashMap<>();
		watches.put("train", trainMat);
		watches.put("test", testMat);

		int round = 10;
		// 学習
		Booster booster = XGBoost.train(trainMat, params, round, watches, null, null);
		// 予測
		float[][] predicts = booster.predict(testMat);

        // 評価用データの正解値
		float[] answers = testMat.getLabel();

		System.out.println("RMSE of predicts: " + calcRMSE(answers, predicts));
	}

	// 正解値と予測値のRMSEを計算
	private static double calcRMSE(float[] answers, float[][] predicts) {
		double sse = 0.0;
		int num = answers.length;

		for (int i = 0; i < num; i++) {
			sse += Math.pow(answers[i] - predicts[i][0], 2);
		}

		return Math.sqrt(sse / num);
	}
}
```

- XGBoost.train() で学習、Booster.predict() で予測を行う

# 参考
- [XGBoostをJavaのwrapperを使用して実行する - TASK NOTES](http://www.task-notes.com/entry/20151024/1445655600)
- [blog.k11i.biz: OS X で XGBoost &#65286; xgboost4j をビルドする手順 2016-03-07 版](http://blog.k11i.biz/2016/03/os-x-xgboost-xgboost4j-2016-03-07.html)
- [LIBSVM Data: Classification, Regression, and Multi-label](https://www.csie.ntu.edu.tw/~cjlin/libsvmtools/datasets/)
- [XGBoost Parameters](https://github.com/dmlc/xgboost/blob/master/doc/parameter.md)