2015年12月31日木曜日

GoogleChart : 時刻入りのグラフを描く

Arduinoから温度を取ってAndroidを中継しデータベースに入れてあります。これをGoogleChartでグラフ表示する方法です。
横軸が時刻が意外に苦労しました。
参考
http://nvnote.com/google-charts-create-graph-xaxis-date/

コントローラ
app]$ vi Controller/SensorsController.php

public function graph($datetime = '2015-12-17') {
                $this->Sensor->recursive = 0;
                $date=date("Y-m-d",strtotime($datetime));
                $this->paginate = array(
                        'conditions'=>array(
                                'Sensor.created BETWEEN ? AND ?' => array($date." 00:00:00", $date." 23:59:59")
                        ),
                        'order' => array('id' => 'asc'),
                        'limit'=>100000,
                );


                $this->set('sensors', $this->Paginator->paginate());
        }
※引数は自由に変更。date関数がちょうどいいかも
findの時、createdの型を指定して範囲を指定し持ってくる
参考
http://d.hatena.ne.jp/YamamoriSansa/20101101/1288611148

ビュー
app]$ vi View/Sensors/graph.ctp
[挿入コード]
コード
注意
・カラムの型をdatetimeにする
 data.addColumn('datetime', '日時');

・created の型が 2015-12-31 17:10:11のようにハイフンで区切られている。Date型が2015/12/31 17:10:11なので文字を変換する。

参考
http://www.ajaxtower.jp/js/date_class/index1.html

表示するとこんな感じ

2015年12月30日水曜日

CentOSへrJavaのインストール

CentOSにRがインストールできたので(http://mizunolab.sist.ac.jp/2015/12/centosr.html)、次はrJavaをインストールする。
rootで作業します。

1.R起動
# R

2.rJavaのインストール
> install.packages('rJava')
Installing package into ‘/usr/lib64/R/library’
‘/usr/lib64/R/library’にインストールされるらしい。

ミラーサイトでJapanを選択

インストールが始まり、1分位かかった。
rootでの作業を終了します。

> q()

利用するユーザに変わります。
# su - ユーザ名

JRI.jarファイルのありかを探す
~]$ ls -l /usr/lib64/R/library/rJava/jri/
とするとありました。

クラスパスの設定をします。R_HOMEの追加もしておきます。
 $ vi .bashrc
export CLASSPATH=/usr/lib64/R/library/rJava/jri/JRI.jar:$CLASSPATH
export R_HOME=/usr/lib64/R




$ source .bashrc

 ソースを書いてみます。
$ vi RSample.java

import org.rosuda.JRI.REXP;
import org.rosuda.JRI.Rengine;

public class RSample {
        public static void main(String[] args) {
                Rengine engine = new Rengine(new String[]{"--no-save"}, false, null);
                engine.assign("a", new int[]{36});
                REXP result = engine.eval("sqrt(a)");
                System.out.println(result.asDouble());
                engine.end();
        }
}



コンパイル
$ javac RSample.java


実行
$ java -Djava.library.path=/usr/lib64/R/library/rJava/jri/ RSample
プロパティを指定して実行します。

ちなみにプロパティを指定しないと、下記になります。

 またR_HOMEが設定されてないと、下記になります。

参考
http://qiita.com/Kentrow@github/items/cdc17f1c65f99a01396f
http://binfalse.de/2011/02/20/talking-r-through-java/

2015年12月28日月曜日

Java : 総組み合わせプログラムの実行

総組み合わせを算出するプログラムを作りました。プログラムとしては貧弱(最低)ですが、実行させることだけ考えて作りました。
プログラムソース

Linuxでベタに実行する方法です。
1.FTP等でファイルのアップロード
今回はパッケージ:roundrobin毎アップロード。今回はホームディレクトリにjavaフォルダを作ってその中にroundrobinをいれます。

2.mysql-connectorの設定
Javaの設定ももちろんですが、コネクタの設定もしておきます。
http://mizunolab.sist.ac.jp/2015/11/linuxjavamysql.html

3.コンパイル、実行
まずサーバにsshで接続します。rootで接続した場合(証明書あり)
# su -ユーザ名
$ cd java
またはユーザで接続する場合
ssh -l ユーザ名 ホスト名

[コンパイル]
java]$ javac roundrobin/*.java

[実行]
java]$ java roundrobin.Roundrobin_main
[データベースの確認]
今回使っているテーブルはcombinationsとpointsの2つです。
combinationsテーブルにアクセスすると、ID、Nのところに値が入ってきます。NはnCrのrの部分のところです。
そこのViewをクリックすると、関係してあるpointsレコードが出力され、ID, Facility_id, Combination_idに値が入ってきます。
※一番最初だけテーブルをtruncateしておいた方が確認しやすいかもしれません。

[総組み合わせの修正]
今回はnCrのnは固定(n=42)、rを変更していきます。
42C41を算出する場合
(1)
java]$ vi roundrobin/Roundrobin_main.java 
int n = 42, k = 41;
kのところが41となっていることを確認します。


(2)java]$ vi roundrobin/Roundrobin_lib.java
for(idx[40] = idx[39]+1 idx[40] < n-k+41; idx[40]++){
・・・
・・・
}//40
のところが有効になっていることを確認します。

(3)コンパイル、実行、確認
java]$ javac roundrobin/*.java
java]$ java roundrobin.Roundrobin_main
データベースも確認します。

42C40を計算する場合
java]$ vi roundrobin/Roundrobin_main.java 
int n = 42, k = 40;
kのところが40に変更。

java]$ vi roundrobin/Roundrobin_lib.java
// for(idx[40] = idx[39]+1 idx[40] < n-k+41; idx[40]++){
//}//40
この2行だけをコメントアウトします。

inputResult(index, idx);
mysql.insertCombination(k, idx);
index++;
はコメントアウトしない
このような感じで42C39を実行する場合も

java]$ vi roundrobin/Roundrobin_main.java 
int n = 42, k = 39;
kのところが39に変更。
 java]$ vi roundrobin/Roundrobin_lib.java

このようにidx[39]のところを対でコメントアウトします。
このように数を減らしていきながら、ファイルのコメントアウトを増やしていきます。

Java : コマンドラインでのコンパイル&実行

ローカルで作ったプロジェクト(MacまたはWindows)をサーバ(Linux)で動かす時に使うコマンドです。
1.Eclipseで作ったプロジェクトを確認
今回は、パッケージ名:roundrobin、クラス:MySQL.java, Roundrobin_lib.java, Roundrobin_main.javaを利用します。

2.FTPでjavaを利用するディレクトリにアップします。
今回はjavaディレクトリを作り、その中にパッケージフォルダ(roundrobin)をいれておきます。




3. コンパイル
java]$ javac roundrobin/*.java

4.実行
java]$ java roundrobin.Roundrobin_main

これで色々できます。

2015年12月26日土曜日

Cakephp : Googlechartでのグラフ表示

Cakephpで作ったページにGooglechartを使ってグラフ表示させました。
最初はいろんなところで提供されているCakephp用のHelperを使おうかと思いましたが、融通を効かせたかったので、本家のJavaScriptをそのままViewにいれて表示させることにしました。やり方は簡単で、表示させたいViewの部分に本家のコードをそのままコピーして、出力を修正するだけです。出力は基本echoでやります。以下挿入したコードです。

 挿入コード

 複数折れ線も表示してみました。
挿入コード





2015年12月25日金曜日

Cakephp : 複数の外部キーの設定

Cakephpで複数の外部キーを設定するときのメモ。
複数の外部キーといっても、同じテーブルに他の同じテーブルの外部キーを複数設定する場合です。つまり、operationsテーブルに2つのoperatorsテーブルのキーがある場合、(operator_id、evaluator_id)をoperationsテーブルに設定します。複数あるので、外部キーと自動的に認識してくれません(ViewではそのままIDとして表示)。

1. Operationsテーブルのモデルに設定
app]$ vi Model/Operation.php

var $belongsTo = array(
                'Operator' =>array('className' => 'Operator','foreignKey' => 'operator'),
                'Evaluator' =>array('className' => 'Operator','foreignKey' => 'evaluator')
        );


あとはもう一度operationsテーブルのviewだけbakeしとけば、認識されるようになります。

2015/12/25追記
2.リレーション側でのbake
OperatorとEvaluatorキーを使う側のbakeではリレーションが自動認識されないので、自分で設定する必要があります。ひとまずOperatorキーがリレーションとして認識されたかったので設定しました。Operatorsテーブルのbakeです。
このあとC,Vと続けてBakeします。

参考
http://www.asterisk-works.jp/wiki/index.php/Bake%E3%83%A1%E3%83%A2

2015年12月16日水曜日

App Inventorのオフラインでの運用

今回高校の模擬授業の内容でApp Inventorをやりました。
学外での授業ということでインターネット接続が使えない環境でしたので、App Inventorをオフライン運用しました。モバイルルータでも良かったのですが、今後のことを考えてあえてオフライン運用にしました。

1.サーバの設定
今回利用したオフラインInventorは、App Inventor 2 Ultimateを利用しました。
http://sourceforge.net/projects/ai2u/files/ai2u%202.8/Installer/
から
AI2U 64bit v2.8.exe
をダウンロードしました。これはWindows版しかなかったので、仮想でWindowsを立ててインストールしました。
ホストOS(MAC)、ゲストOS:Inventorサーバ(WIndows)ともプライベートアドレスを振りました。ゲストOSはブリッジ接続です(NATではありません)。
ホストOS : 192.168.0.100/24
ゲストOS : 192.168.0.101/24
※学内ではグローバルIPを使っているので、そのままの環境でやろうとしたが、なぜか繋がらず。(多分できるはずだが、時間がなかったのでプライベートアドレスを振り直した。)

2.クライアント側の設定
今回はMACを使いました。
http://appinventor.mit.edu/explore/ai2/mac.html
からダウンロードして、インストールしました(デフォルト)。
今回MACを使った理由は
・AI Companionでのアプリ転送はローカルではできない(と思う)
・AI Companionを使わず、USBで転送することが必要。
USB転送がMACは簡単にできたが、Windowsではドライバの関係かすぐできなかった(時間がなくて)。
クライアントPC : 192.168.0.102〜/24

3.無線環境
無線APを用意。WAN接続はなく、単なるブリッジとして利用。
タブレットはUSB転送なので、接続しない。

4.課題
・クライアントPCがWindowsで出来ればもっと汎用的になる
・グローバルIPのままできれば学内の環境のまま持っていける
・準備は早めに

今回はインターネット環境に頼らず、オフラインで運用できたので運用の幅が広がったと思います。新たなクラウド環境(オフライン:持ち運び可能なオンプレミス)かな? ここまで2時間で準備ができて授業間に合いました。一安心です。
とにかく、準備は早めに(まわりが迷惑)。

2015年12月13日日曜日

CentOSへRのインストール

Rを使うための基本設定として、まずサーバにRをインストールします。

rootで
# yum install R
インストールが終了し(結構かかった68パッケージ)ユーザに変えて起動してみる。
 $ R
> 3+4
[1] 7
> sin(pi/6)
[1] 0.5
> q()

動いているのが確認できた。ひとまず区切りとして次回rjavaをインストールして、JavaからRを動かしてみる。

追記
epelリポジトリが必要な場合
$ yum -y install yum-priorities
$ wget http://ftp-srv2.kddilabs.jp/Linux/distributions/fedora/epel/6/x86_64/epel-release-6-8.noarch.rpm
$ rpm -ivh epel-release-6-8.noarch.rpm
$ yum --enablerepo=epel -y install R

参考
https://gist.github.com/ochilab/5883781

2015年12月10日木曜日

CakephpでのPOST処理

CakephpでのPOST処理のメモです。

[Cakephp側]
scoresテーブル用意
このテーブルをbakeしておきます。addアクションを利用してpostアクションを作成します。
app]$ vi Controller/ScoresController.php

addアクションをコピーして、postアクションとして、青の部分を追加します。
public function post() {

                $name = $this->request->data('name');
                $score = $this->request->data('score');


                if ($this->request->is('post')) {
                        $this->Score->create();
                        $this->request->data['Score']['name'] = $name;
                        $this->request->data['Score']['score'] = $score;


                        if ($this->Score->save($this->request->data)) {
                                $this->Session->setFlash(__('The score has been saved.'));
                                return $this->redirect(array('action' => 'index'));
                        } else {
                                $this->Session->setFlash(__('The score could not be saved. Please, try again.'));
                        }
                }

        }
※修正
post関数を用意してもよいが、フィールド名が同じであればadd関数のまま使える。

[Android側]
POSTの送り先:
String urlinput = "http://ホスト名/scores/post";
ソースコード:PostService 

Android側でPOST送信をします。
Cakephp側ではその情報を受け取り、DBに格納します。

 
参考
http://qiita.com/kazu56/items/7d344ccef56deef66a7a 

2015年12月9日水曜日

multiple insertの利用(StringBuffer併用)

データベースの連続Insertの時に、かなり速度が遅くります。
multiple insertを使うことで劇的に改善されました。



INSERT INTO table名 (カラム1, カラム2, カラム3) VALUES (データ1, データ2, データ3), (データ4, データ5, データ6), (データ7, データ8, データ9), (・・・);
このようにvalues以下を並べて書けばいいです。SQLを発行するのは1回だけとなります。
参考
http://qiita.com/jkr_2255/items/12081b3c066d371516f5

Javaで利用するとき、valuesのところが文字列連結になってきます。今回繰り返し数が多いのでStringBufferを使いました。これもかなり早い。
参考
http://www.techscore.com/blog/2012/11/29/%E6%96%87%E5%AD%97%E5%88%97%E7%B5%90%E5%90%88-java%E7%B7%A8/

[利用例]
StringBuffer buf = new StringBuffer();
buf.append("INSERT INTO points(hospital_id, calclation_id,dea) VALUES");
for(int i = 0; i < constraint.length; i++){
    double dea = (var[2]*constraint[i][2] + var[3]*constraint[i][3])/(var[0]*(-1)*constraint[i][0]+var[1]*(-1)*constraint[i][1]);
    if(i == constraint.length -1)
        buf.append("("+hospital_id[i]+","+calclation_id+","+dea+")");
    else
        buf.append("("+hospital_id[i]+","+calclation_id+","+dea+"),");
}
String sql4 = buf.toString();
stmt.execute (sql4);