著者アーカイブ 村上

村上 著者:村上

【備忘録】多次元の連想配列を複数の条件でソートする方法

PHPで多次元の連想配列のソートをする機会があったので、備忘録として。

ソートには、「array_multisort()」という複数または多次元の配列をソートできる関数を利用します。

array_multisort()関数のマニュアルについてはこちらから。
http://php.net/manual/ja/function.array-multisort.php

 

今回はサンプルとして、下記のようなデータを使用します。
こちらのデータを、年齢誕生月の昇順で並び替えを行います。

$data = array(
    array("no" => "1", "name" => "田中", "age" => 30, "birth_month" => 6),
    array("no" => "2", "name" => "鈴木", "age" => 15, "birth_month" => 8),
    array("no" => "3", "name" => "山田", "age" => 22, "birth_month" => 11),
    array("no" => "4", "name" => "遠藤", "age" => 30, "birth_month" => 9)
);

 

まず、ソートしたい列のデータを取り出し、ソート用の配列を作ります。
今回は、年齢と誕生月でソートしたいので、$tmp_age$tmp_bmonthという配列を用意し、それぞれに年齢と誕生月のデータを格納します。

foreach ($data as $key => $value) {
    $tmp_age[$key] = $value["age"];  // $tmp_age に年齢データ格納
    $tmp_bmonth[$key] = $value["birth_month"];  // $tmp_bmont に誕生月データ格納
}

 

ソート用の配列に各データを格納出来たら、array_multisort()関数でソートします。
関数の引数には、「ソートしたい列データの配列」、「ソート順」、「ソート条件」という組み合わせを条件分だけ繰り返し、最後にソートしたい連想配列を指定します。
なお、「ソート順」、「ソート条件」については省略可能で、省略した場合は昇順になります。

array_multisort($tmp_age, SORT_ASC,  // 年齢データを昇順でソート
                $tmp_bmonth, SORT_ASC,  // 誕生月データを昇順でソート
                $data);  // ソートしたい連想配列

なお array_multisort()は、成功した場合には TRUE を、失敗した場合に FALSE を返します。

 

ソート後の連想配列を var_dump で取り出してみた結果がこちら。

array(4) {
  [0]=>
  array(4) {
    ["no"]=>
    string(1) "2"
    ["name"]=>
    string(6) "鈴木"
    ["age"]=>
    int(15)
    ["birth_month"]=>
    int(8)
  }
  [1]=>
  array(4) {
    ["no"]=>
    string(1) "3"
    ["name"]=>
    string(6) "山田"
    ["age"]=>
    int(22)
    ["birth_month"]=>
    int(11)
  }
  [2]=>
  array(4) {
    ["no"]=>
    string(1) "1"
    ["name"]=>
    string(6) "田中"
    ["age"]=>
    int(30)
    ["birth_month"]=>
    int(6)
  }
  [3]=>
  array(4) {
    ["no"]=>
    string(1) "4"
    ["name"]=>
    string(6) "遠藤"
    ["age"]=>
    int(30)
    ["birth_month"]=>
    int(9)
  }
}

年齢・誕生月で正しくソートできました。

 

単に連想配列の昇順・降順のみでしたら、asort()arsort() を利用すれば良いのですが、多次元の連想配列で、かつソートの条件が複数の場合は、ソート用の配列が要るなど、少しややこしかったですね。
が、今後利用する機会が多々ありそうなやり方でしたので、きちんと覚えたいと思います。

村上 著者:村上

【備忘録】jQueryの要素追加のメソッド一覧

現在開発中のWebシステムでjQueryでの要素追加メソッドを使うことがあったのですが、すぐに忘れてしまうのでまとめてみました。
ちなみに私は、.after()や.before()などは、名前の通りのメソッドなのでわかりやすいし覚えやすいのですが、.append().prepend()あたりを忘れやすいです。

 

.after()

$('div').after('追加要素');

一番わかりやすいし、使いやすいので、比較的利用頻度が高めなメソッドです。
指定した要素のすぐ後ろに、要素を追加します。

上のコードを実行するとこんな感じになります。
なお、今回掲載しているサンプルコードでは、div要素に対して、p要素を追加しています。

<div>基準となるdiv要素</div>
<p>追加したp要素</p>  <!-- after()で追加したp要素 -->

 
似たようなメソッドとして、.insertAfter()があります。

$('追加要素').insertAfter('div');

実行結果は、上で記載した.after()と同じになります。
追加したい要素と、追加の基準となる要素の順番が逆になるので、こちらは少し分かりにくい印象を受けます。

 

.before()

$('div').before('追加要素');

こちらは.after()と似ていますが、指定した要素のすぐ前に要素を追加するメソッドです。
分かりやすいですが、今まで書いたコードの中ではそこまで使用頻度は高くなかったです。
 

<p>追加したp要素</p>  <!-- before()で追加したp要素 -->
<div>基準となるdiv要素</div>

 
こちらのbeforeにも、似たようなメソッドとして、.insertBefore()があります。

$('追加要素').insertBefore('div');

こちらの実行結果は、上で記載した.before()と同じになります。

 

.append()

$('div').appand('追加要素');

こちらも良く使うメソッド。
指定した要素の中に、要素を追加します。
 

<div>
    <b>元々記述してあったb要素</b>
    <p>追加したp要素</p>  <!-- append()で追加したp要素 -->
</div>

なお、要素を追加するときは、指定した要素(今回はdiv要素)の一番後ろに要素が追加されます。
 
似たようなメソッドとしては、.appendTo()があります。

$('追加要素').appendTo('div');

実行結果は上で記載した.append()のサンプルと同じ結果になります。

 

.prepend()

$('div').before('追加要素');

こちらは.append()メソッドと似ていますが、指定した要素の一番前に要素が追加されます。
 

<div>
    <p>追加したしたp要素</p>  <!-- prepend()で追加したp要素 -->
    <b>元々記述してあったb要素</b>
</div>

こちらは使用頻度は低め、というかまだ実際に使ったことはないですね。
 
こちらにも似たようなメソッドとして、.prependTo()があります。

$('追加要素').prependTo('div');

実行結果は上で記載した.prepend()のものと同じです。

 

ざっくりとまとめましたが、要素を追加するメソッドとしてはこのあたりを知っていればいいかと思います。
他にも.wrap()メソッドという、指定した要素で対象の要素を囲むメソッドもありますが、こちらは使う機会はあまりないかと思い、割愛させていただきました。
もし間違っている場合は、そっとご指摘をお願いします。

村上 著者:村上

Safariで「YYYY-MM-DD HH:II:SS」形式をDate.parse()するとNaNを返す問題とその対処法について

昨日この仕様でハマったので覚え書きもかねて。

JavascriptのDate.parse()とは、カッコ内の日時文字列を解析して、1970年1月1日 00:00:00からのミリ秒数に変換してくれる関数です。
具体的には下記のように使用します。

Date.parse('Thu, 1 Nov 2017 13:41:00 GMT+0900');
// =1509511260000

が、この解析できる日付文字列の形式が限られており、よくデータベースで用いられている「YYYY-MM-DD HH:II:SS」形式の日付文字列を入れてしまうとNaNを返すとのこと。

どうやら文字列の中にハイフンが入っていることが原因のようです。
また、Date.parse()だけではなく、new Date()のなかにハイフンを用いた日付文字列を入れた場合でも、同じくNaNを返す仕様になっているとのこと。
なお、一部のブラウザでは、ハイフンにも対応しているようで Google Chrome では、「YYYY-MM-DD HH:II:SS」形式でも、正しくミリ秒数が返ってきました。
普段使用しているブラウザが Google Chrome だったため、他ブラウザで動作検証するまで気が付きませんでした。

 

こちらの仕様については、ハイフンスラッシュに置換することで対応できました。
具体的なコードはこちら。

Date.parse([日付文字列].replace(/-/g , "/"));

replace関数を用いて、ハイフンをスラッシュに置換することで、無事日付のミリ秒数が取得できました。

 

以上、今回私がハマったJavascriptの関数でした。
そもそも、日付をミリ秒数に変換するなんてこと早々しないので、実際に触ってみるまで、こんな仕様になっているとは全く知りませんでした。
原因がわかってしまえば対処は難しくありませんでしたが、知らないと原因特定までに時間がかかりそうな仕様でしたので、Javascriptで日付を扱うときは十分お気を付けください。

村上 著者:村上

【イベントレポ】「第22回 テクノフェスタ in 浜松」に参加しました

少し前のことになりますが、11月11日(土)、12日(日)に静岡大学浜松キャンパスで開催されていた「テクノフェスタ in 浜松」に行ってきましたので、こちらのイベントレポです。

テクノフェスタについてはこちらの静大のHPもご確認ください。

第22回 テクノフェスタ in 浜松
http://www.eng.shizuoka.ac.jp/campuslife/festa/

様々な展示や体験ブースがありましたが、今回のお目当てはこちらの2ブース。

遊橋研究室


静岡大学生向けの時間割管理のスマートフォンアプリや、学生が開発したブロック崩しゲームが展示されていました。
ゲームに夢中になっているお子様が多く、ブースの写真は撮影できませんでした。
ブースの対面の壁には、各アプリのQRコードが貼られており、こちらから自由にインストールすることが可能でした。

木谷研究室


「RTK宝探し・リターンズ」という実験が行われており、プレイヤーは司令部と探検部に分かれて構内に隠された宝箱を探すというものでした。
RTK(Realtime Kinematic、リアルタイムキネマティック)とは、「GNSS基準局受信機を固定化して、もう一方の受信機で移動しながら各観測位置をリアルタイムに測位していくこと」です。
詳細については、こちらの「静岡大学・浜松キャンパスにGNSS基準局受信機」をご覧ください。

あまり詳しくない工学系の展示でも、こういうイベントだとつい足を止めてみてしまいます。
専門外の技術に興味をもてる良い機会でした。

また、大学祭も同日開催していたため、高校生やお子様連れのご家族の方が多くいらっしゃいました。
特に、子供向けの実験を行える「キッズ・サイエンス」ブースは大盛況でした。
子供向けとありましたが、成人済みの私も是非体験してみたかったですね。