質問をすることでしか得られない、回答やアドバイスがある。

15分調べてもわからないことは、質問しよう!

新規登録して質問してみよう
ただいま回答率
85.48%
CSV

CSV(Comma-Separated Values)はコンマで区切られた明白なテキスト値のリストです。もしくは、そのフォーマットでひとつ以上のリストを含むファイルを指します。

多次元配列

1次元配列内にさらに配列を格納している配列を、多次元配列と呼びます。

PHP

PHPは、Webサイト構築に特化して開発されたプログラミング言語です。大きな特徴のひとつは、HTMLに直接プログラムを埋め込むことができるという点です。PHPを用いることで、HTMLを動的コンテンツとして出力できます。HTMLがそのままブラウザに表示されるのに対し、PHPプログラムはサーバ側で実行された結果がブラウザに表示されるため、PHPスクリプトは「サーバサイドスクリプト」と呼ばれています。

Q&A

解決済

3回答

9058閲覧

phpでcsvファイル内の特定の数値項目の値順にソートし、値がない場合も欠番としてデフォルト値を表示させる方法

singlestroke

総合スコア68

CSV

CSV(Comma-Separated Values)はコンマで区切られた明白なテキスト値のリストです。もしくは、そのフォーマットでひとつ以上のリストを含むファイルを指します。

多次元配列

1次元配列内にさらに配列を格納している配列を、多次元配列と呼びます。

PHP

PHPは、Webサイト構築に特化して開発されたプログラミング言語です。大きな特徴のひとつは、HTMLに直接プログラムを埋め込むことができるという点です。PHPを用いることで、HTMLを動的コンテンツとして出力できます。HTMLがそのままブラウザに表示されるのに対し、PHPプログラムはサーバ側で実行された結果がブラウザに表示されるため、PHPスクリプトは「サーバサイドスクリプト」と呼ばれています。

1グッド

0クリップ

投稿2016/12/07 08:09

下記のようなcsvファイルがあり、

csv

1seq,house,booth 21,家A,1 32,家A,6 43,家A,3 54,家B,1 65,家B,2

phpで
・「家A」のみを抽出し
・「booth」で昇順にし、
・「booth」を連番となるようにして下記のように表示させたいです。

HTML

1<ul> 2 <li>1:家A</li> 3 <li>2:無し</li> 4 <li>3:家A</li> 5 <li>4:無し</li> 6 <li>5:無し</li> 7 <li>6:家A</li> 8</ul>

データ内に「booth」のデータがない場合(※今回では2,4,5のような場合)でも「無し」と表示されるようにしたいのですが、その部分が分かりません。

下記のように記述してみたのですが、

php

1function sampleFunc () { 2 3 // ローケルを設定 4 setlocale(LC_ALL, 'ja_JP.UTF-8'); 5 $filename = FILEPATH; 6 $tempCSV = file_get_contents($filename); 7 $tempCSV = mb_convert_encoding($tempCSV, 'UTF-8', 'SJIS'); 8 $fp = tmpfile(); 9 fwrite($fp, $tempCSV); 10 rewind($fp); 11 12 $lineCount = 0; 13 // 1行ずつ読み込み 14 while ($arr = fgetcsv($fp)) { 15 // 空行を除外 16 if (!array_diff($arr, array(''))) { 17 continue; 18 } 19 // 1行目をスキップ 20 if ($lineCount === 0) { 21 $lineCount++; 22 continue; 23 } 24 25 list ($seq, $house, $booth) = $arr; 26 27 $datas[] = array( 28 'seq'=>$arr[0], 29 'house'=>$arr[1], 30 'booth'=>$arr[2] 31 ); 32 } 33 34 // ファイルを閉じる 35 fflush ($fp); 36 flock($fp, LOCK_UN); 37 fclose($fp); 38 39 // floorの順番にソート 40 sortArrayByKey($datas, "booth"); 41 42 // HTML部分を表示 43 echo "<ul>"; 44 foreach ($datas as $line) { 45 // 家Aなら 46 if ($line["house"] === "家A") { 47 echo "<li>".$line["booth"].":".$line["house"]."</li>\n"; 48 } 49 } 50 echo "</ul>"; 51 52} 53 54// 多次元配列をソート 55function sortArrayByKey( &$array, $sortKey, $sortType = SORT_ASC ) { 56 $tmpArray = array(); 57 foreach ( $array as $key => $row ) { 58 $tmpArray[$key] = $row[$sortKey]; 59 } 60 array_multisort( $tmpArray, $sortType, $array ); 61 unset( $tmpArray ); 62}

実行すると下記のように表示されてしまいます。

HTML

1<ul> 2<li>1:家A</li> 3<li>3:家A</li> 4<li>6:家A</li> 5</ul>

解決方法を教示いただけますと幸いです。
よろしくお願いいたします。

KiyoshiMotoki👍を押しています

気になる質問をクリップする

クリップした質問は、後からいつでもMYページで確認できます。

またクリップした質問に回答があった際、通知やメールを受け取ることができます。

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

guest

回答3

0

ベストアンサー

csvの読み込み時にちょっと工夫すればすぐでしょう

PHP

1<?PHP 2$fp=fopen("xxx.csv","r"); 3while(($data=fgetcsv($fp))!=false){ 4 if($data[1]=="家A") $datas[$data[2]]="家A"; 5} 6fclose($fp); 7ksort($datas); 8$datas=array_replace_recursive(array_fill(array_keys($datas)[0],array_keys($datas)[count($datas)-1],"なし"),$datas); 9foreach($datas as $key=>$val){ 10 print htmlspecialchars("<li>$key:$val</li>\n"); 11}

追記

複数項目を表示

PHP

1<?PHP 2$fp=fopen("xxx.csv","r"); 3while(($data=fgetcsv($fp))!=false){ 4 if($data[1]=="家A") $datas[$data[2]]=["home"=>"家A","price"=>$data[3]]; 5} 6fclose($fp); 7ksort($datas); 8$datas=array_replace_recursive(array_fill(array_keys($datas)[0],array_keys($datas)[count($datas)-1],["home"=>"なし","price"=>""]),$datas); 9foreach($datas as $key=>$val){ 10 print htmlspecialchars("<li>$key:{$val["home"]}".($val["price"]?":":"")."{$val["price"]}</li>"); 11}

投稿2016/12/07 08:44

編集2016/12/07 11:28
yambejp

総合スコア114769

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

singlestroke

2016/12/07 09:45

上記の通りでできました。ありがとうございます。 今後csvファイルの項目が増えた際に(例えばprice、periodなど)、同様に<li>タグ内に表示させたい場合はどのようにしたらよいのでしょうか。 申し訳ありません。よろしくお願いいたします。
yambejp

2016/12/07 11:29

複数項目を表示したいとのことですので追記しときました
singlestroke

2016/12/07 13:49

ありがとうございます。
guest

0

PHP

1 // HTML部分を表示 2 echo "<ul>"; 3 foreach ($datas as $line) { 4 // 家Aなら 5 if ($line["house"] === "家A") { 6 echo "<li>".$line["booth"].":".$line["house"]."</li>\n"; 7 } 8 } 9 echo "</ul>";

上記の部分を下記のようにしてはどうですか?(足りない部分を補足するようにする)

PHP

1 // HTML部分を表示 2 echo "<ul>"; 3 // インデックスの開始値を設定 4 $boothIndex = 1; 5 foreach ($datas as $line) { 6 // 家Aなら 7 if ($line["house"] === "家A") { 8 // ここでインデックスの不足分を生成 9 for(; $boothIndex < $line["booth"]; $boothIndex++) { 10 echo "<li>".$boothIndex.":無し</li>\n"; 11 } 12 13 echo "<li>".$line["booth"].":".$line["house"]."</li>\n"; 14 } 15 $boothIndex+;; 16 } 17 echo "</ul>";

投稿2016/12/07 08:23

himakuma

総合スコア952

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

0

家A以外は「無し」というのでしたら、こちらでどうでしょうか。

if ($line["house"] === "家A") { echo "<li>".$line["booth"].":".$line["house"]."</li>\n"; }else { echo "<li>".$line["booth"].":無し</li>\n"; }

投稿2016/12/07 08:16

namimon

総合スコア726

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

15分調べてもわからないことは
teratailで質問しよう!

ただいまの回答率
85.48%

質問をまとめることで
思考を整理して素早く解決

テンプレート機能で
簡単に質問をまとめる

質問する

関連した質問