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

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

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

PDO(PHP Data Objects)はPHPのデータベース抽象化レイヤーです。

PHP

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

データベース

データベースとは、データの集合体を指します。また、そのデータの集合体の共用を可能にするシステムの意味を含めます

Q&A

解決済

5回答

31401閲覧

PHP fetchAllメソッドって何で使うんですか?

marimokomokmOk

総合スコア52

PDO

PDO(PHP Data Objects)はPHPのデータベース抽象化レイヤーです。

PHP

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

データベース

データベースとは、データの集合体を指します。また、そのデータの集合体の共用を可能にするシステムの意味を含めます

1グッド

5クリップ

投稿2017/03/13 11:11

編集2017/03/13 11:35

なんでfetchAllメソッド使うんですか?
SBCreativeのPHP超入門になんどもfetchAllで取得してforeachでまわしてる文が出てくるんですけど未だに理解してません。

fetchAll()→該当する全てのデータを配列として返す

という意味みたいなんですが、
該当するデータなんて一件ぐらいしかないのになんで
わざわざ全てのデータを配列として返すfetchAllを使うんですか?

なんども
foreach ( $stmt->fetchAll () as $row ) {
がでてきて意味が解りません。

php

1foreach ( $stmt->fetchAll () as $row ) { 2 $_SESSION ['customer'] = array ( 3 // idというキーで$row['id']を入れる 4 'id' => $row ['id'], 5 'name' => $row ['name'], 6 'address' => $row ['address'], 7 'login' => $row ['login'], 8 'password' => $row ['password'] 9 ); 10}

コード

php

1<?php require 'menu.php'; ?> 2<?php 3session_start (); 4// unset→指定した変数を破棄する 5unset ( $_SESSION ['customer'] ); 6$pdo = new PDO ( 'mysql:host=localhost;dbname=takahashi1;charset=utf8', 'takahashi', 'takahashi' ); 7$stmt = $pdo->prepare ( 'select * from customer where login=? and password=?' ); 8// var_dump($stmt); 9$stmt->execute ( array ( 10 $_POST ['login'], 11 $_POST ['password'] 12) ); 13 14// foreachは配列とオブジェクトをループして使うための構文 15// 配列ではないが使いやすくするために特別にforeachの反復処理で使えるように作られている 16// $rowという変数に入れる 17// $rows = $stmt->fetchAll (); 18// var_dump($rows) 19foreach ( $stmt->fetchAll () as $row ) { 20// foreach ( $rows as $row ) { 21 // 連想配列$_SESSION['customer']にキーを指定して追加し、値として連想配列を代入 22 $_SESSION ['customer'] = array ( 23 // idというキーで$row['id']を入れる 24 'id' => $row ['id'], 25 'name' => $row ['name'], 26 'address' => $row ['address'], 27 'login' => $row ['login'], 28 'password' => $row ['password'] 29 ); 30} 31if (isset ( $_SESSION ['customer'] )) { 32 echo 'いらっしゃいませ、', $_SESSION ['customer'] ['name'], 'さん。'; 33} else { 34 echo 'ログイン名またはパスワードが違います。'; 35} 36?>

なんでここではfetchじゃなくてfetchAllなのでしょうか。
fetchとfetchAllの使い分けもできません。

fetch→一行づつ取得
fetchAll→全データを配列に変換。全ての結果行を含む配列を返す

norisukeoji👍を押しています

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

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

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

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

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

guest

回答5

5

たとえば、PHPのマニュアルには次のような記述があります。

PDO::query() を次にコールする前に 結果セット内の全てのデータを取得しない場合、そのコールは失敗します。 PDOStatement::closeCursor() をコールし、 次に PDO::query() をコールする前に PDOStatement オブジェクトに関連付けられたリソースを解放してください。
--- PDO::query

fetch()を使って1行だけ取得すると、問い合わせが複数の行を返した場合に、この罠にはまります。

本の執筆者の気持ちになって考えると、fetchAll()を使っておけば複数の行が返されても安心だし、2種類のやりかたを説明するより簡単になります。


「『超』入門」と銘打った本に、なんでも書いてあるはずがないです。試読版の目次をみると、データベース操作には80ページほどを割いているのがわかりますが、この分量で細かい解説までできるはずもありません。

同書の最後のほうには「PHPの学習方法」という節もあるので、読んでみると参考になることが書いてあるのではないでしょうか。

そこにもおそらく書いてあるでしょうけれど、わからないことがあったらまず PHPのマニュアルを調べるようにして下さい。PHPというプログラミング言語の情報のほとんどすべては、これに書いてあります。

投稿2017/03/14 09:13

ikedas

総合スコア4139

_Taturon_, KiyoshiMotoki, kei344, marimokomokmOk👍を押しています

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

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

marimokomokmOk

2017/03/15 02:47

ご解答いただきありがとうございます。 PDO::query() を次にコールする前に 結果セット内の全てのデータを取得しない場合、そのコールは失敗します。 PDOStatement::closeCursor() をコールし、 次に PDO::query() をコールする前に PDOStatement オブジェクトに関連付けられたリソースを解放してください。 --- PDO::query ↑ 理解できないのでよく読んでみます
ikedas

2017/03/15 03:03

query()ではなくprepare()とexecute()を使う場合のcloseCursor()の使い方は、マニュアルのPDOStatement::closeCursorに「例1」として載っています。参考まで。
guest

5

どうしてfoeach($stmt->fetchAll() as $row)なんて訳のわからない書き方してるんだろうと先日から不思議に思ってたのだが、
その本のせいだったか。
https://teratail.com/questions/67446
https://teratail.com/questions/68380
https://teratail.com/questions/68529

戻りが1行だけならfetch()で問題ないし、
複数行ならそもそもPDOStatementをそのままforeachすればいい。

単純にその本が駄目ってことでいいんじゃないですかね。

投稿2017/03/13 11:44

編集2017/03/13 11:45
rana_kualu

総合スコア92

masa_mf3, kei344, s8_chu, marimokomokmOk, SVC34👍を押しています

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

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

marimokomokmOk

2017/03/13 11:49

ありがとうございます 本がだめなんですね この本毎日使ってるんですが><。。。
ockeghem

2017/03/14 08:52

その本、最近確認しましたが、サンプルプログラムに脆弱性がすごく多いので、その本の通り書いたら脆弱性だらけのアプリケーションになりますよ
ikedas

2017/03/15 00:58

脆弱性については、具体的に指摘しなければ対策ができないまま不安を煽るだけになるので、逆効果ではないでしょうか (コードを書かないのが一番安全だ、ということならそれでもいいですが。冗談です)。 また、「入門」レベルの書籍にどのようなことを求めるのか、という観点もあると思います。
marimokomokmOk

2017/03/15 05:09

この本を愛読していたのに残念です悲 SBCreativeに問い合わせてみます! while ( $row = $stmt->fetch ( PDO::FETCH_ASSOC ) ) { の意味が未だにわからない私ってなんなのでしょうか。。。 昨日に引き続き一日中調べてますがわかりません。。 窓際族になってきました。
yodel

2017/03/15 05:22

1行ずつfetchして$rowに設定して、$rowの中身をループの中で毎回処理して、 中身が無くなったらfetchの返り値がfalseになってループを抜ける感じです。
marimokomokmOk

2017/03/15 07:52

ありがとうございます。わかりやすいです!! $rowにfetchで取れたid name address login passwordなどの中身が代入されて、$rowの中身がある限りの間繰り返すということでしょうか。
ockeghem

2017/03/15 12:44

そうですね。ブログ等で具体的に示すことにします
marimokomokmOk

2017/03/16 05:02

松浦様からメールの返信をいただきました。 ↓ 松浦と申します。 『確かな力が身につくPHP「超」入門』をお読み頂き誠にありがとうございます。 情報を頂きありがとうございます。 本書のサンプルにおいて、 foreach ($sql->fetchAll() as $row) { のように記述している箇所は、 foreach ($sql as $row) { のように、簡潔に記述することができます。 検索結果をいったん配列として保存し、後で色々な 処理を加える場合には fetchAllメソッドが使えますが、本書のサンプルでは検索結果をforeachで一度処 理すれば済むので、より簡潔な後者の記述が適していたと存じます。 (whileとfetchを使う方法もありますが、本書の場合には上記の後者が妥当かと 存じます。) お手数をおかけして誠に申し訳ございません。 どうぞ宜しくお願い申し上げます。
guest

2

fetchAllしたら全データが抜き出せるんですから、
別のライブラリに渡すときには便利ですよね

現行ステートメント文がforeachで回せるようになっているので
全データ得なくても細かく処理はしやすいですよね

PHP

1$stmt = $pdo->query('SELECT * FROM Entry'); 2foreach ($stmt as $row) { 3 print_r($row); 4}

投稿2017/03/13 12:19

yambejp

総合スコア114339

masa_mf3, marimokomokmOk👍を押しています

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

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

marimokomokmOk

2017/03/14 02:48

ご解答いただきありがとうございます。 申し訳ございません、私には理解できないのでよく読んでみます。
guest

1

ベストアンサー

fetchAllで取得した配列をあとで使いまわすなら意味があるけど、今回のコードではforeach内で使っていて配列自体はどこにも格納していないので、意味がないですね。
ご指摘の通り、単なるfetchの方が適切かと思います。
また抽出されるレコード数が巨大な場合、一旦配列として受け取るので、レスポンスの面でも不安があります。

投稿2017/03/13 23:41

ttyp03

総合スコア16996

marimokomokmOk👍を押しています

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

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

marimokomokmOk

2017/03/14 02:28

ご解答いただきありがとうございます。 fetchAll()をfetch()に変えたらエラーになってしまいました。 Warning: Illegal string offset 'id' in /home/takahashi/public_html/login-output.php on line 25 Warning: Illegal string offset 'name' in /home/takahashi/public_html/login-output.php on line 26 Warning: Illegal string offset 'address' in /home/takahashi/public_html/login-output.php on line 27 Warning: Illegal string offset 'login' in /home/takahashi/public_html/login-output.php on line 28 Warning: Illegal string offset 'password' in /home/takahashi/public_html/login-output.php on line 29 Warning: Illegal string offset 'id' in /home/takahashi/public_html/login-output.php on line 25 Warning: Illegal string offset 'name' in /home/takahashi/public_html/login-output.php on line 26 Warning: Illegal string offset 'address' in /home/takahashi/public_html/login-output.php on line 27 Warning: Illegal string offset 'login' in /home/takahashi/public_html/login-output.php on line 28 Warning: Illegal string offset 'password' in /home/takahashi/public_html/login-output.php on line 29 Warning: Illegal string offset 'id' in /home/takahashi/public_html/login-output.php on line 25 Warning: Illegal string offset 'name' in /home/takahashi/public_html/login-output.php on line 26 Warning: Illegal string offset 'address' in /home/takahashi/public_html/login-output.php on line 27 Warning: Illegal string offset 'login' in /home/takahashi/public_html/login-output.php on line 28 Warning: Illegal string offset 'password' in /home/takahashi/public_html/login-output.php on line 29 Warning: Illegal string offset 'id' in /home/takahashi/public_html/login-output.php on line 25 Warning: Illegal string offset 'name' in /home/takahashi/public_html/login-output.php on line 26 Warning: Illegal string offset 'address' in /home/takahashi/public_html/login-output.php on line 27 Warning: Illegal string offset 'login' in /home/takahashi/public_html/login-output.php on line 28 Warning: Illegal string offset 'password' in /home/takahashi/public_html/login-output.php on line 29 Warning: Illegal string offset 'id' in /home/takahashi/public_html/login-output.php on line 25 Warning: Illegal string offset 'name' in /home/takahashi/public_html/login-output.php on line 26 Warning: Illegal string offset 'address' in /home/takahashi/public_html/login-output.php on line 27 Warning: Illegal string offset 'login' in /home/takahashi/public_html/login-output.php on line 28 Warning: Illegal string offset 'password' in /home/takahashi/public_html/login-output.php on line 29 Warning: Illegal string offset 'id' in /home/takahashi/public_html/login-output.php on line 25 Warning: Illegal string offset 'name' in /home/takahashi/public_html/login-output.php on line 26 Warning: Illegal string offset 'address' in /home/takahashi/public_html/login-output.php on line 27 Warning: Illegal string offset 'login' in /home/takahashi/public_html/login-output.php on line 28 Warning: Illegal string offset 'password' in /home/takahashi/public_html/login-output.php on line 29 Warning: Illegal string offset 'id' in /home/takahashi/public_html/login-output.php on line 25 Warning: Illegal string offset 'name' in /home/takahashi/public_html/login-output.php on line 26 Warning: Illegal string offset 'address' in /home/takahashi/public_html/login-output.php on line 27 Warning: Illegal string offset 'login' in /home/takahashi/public_html/login-output.php on line 28 Warning: Illegal string offset 'password' in /home/takahashi/public_html/login-output.php on line 29 Warning: Illegal string offset 'id' in /home/takahashi/public_html/login-output.php on line 25 Warning: Illegal string offset 'name' in /home/takahashi/public_html/login-output.php on line 26 Warning: Illegal string offset 'address' in /home/takahashi/public_html/login-output.php on line 27 Warning: Illegal string offset 'login' in /home/takahashi/public_html/login-output.php on line 28 Warning: Illegal string offset 'password' in /home/takahashi/public_html/login-output.php on line 29 Warning: Illegal string offset 'id' in /home/takahashi/public_html/login-output.php on line 25 Warning: Illegal string offset 'name' in /home/takahashi/public_html/login-output.php on line 26 Warning: Illegal string offset 'address' in /home/takahashi/public_html/login-output.php on line 27 Warning: Illegal string offset 'login' in /home/takahashi/public_html/login-output.php on line 28 Warning: Illegal string offset 'password' in /home/takahashi/public_html/login-output.php on line 29 Warning: Illegal string offset 'id' in /home/takahashi/public_html/login-output.php on line 25 Warning: Illegal string offset 'name' in /home/takahashi/public_html/login-output.php on line 26 Warning: Illegal string offset 'address' in /home/takahashi/public_html/login-output.php on line 27 Warning: Illegal string offset 'login' in /home/takahashi/public_html/login-output.php on line 28 Warning: Illegal string offset 'password' in /home/takahashi/public_html/login-output.php on line 29 いらっしゃいませ、1さん。
ttyp03

2017/03/14 02:31

ああ、いや、単純に置き換えろって話をしたわけではなく、こういう使い方ならfetchで処理した方がいいよねってことです。 fetchにする場合はマニュアルとか参考にして実装してみてください。 http://php.net/manual/ja/pdostatement.fetch.php
marimokomokmOk

2017/03/14 02:40

ありがとうございます。 fetchに変える方法を調べてみます。
marimokomokmOk

2017/03/15 08:44

PDO::FETCH_ASSOC: は、結果セットに 返された際のカラム名で添字を付けた配列を返します。 ↑ この意味がわかりません
ttyp03

2017/03/15 09:15

質問内容と趣旨がずれてきています。 一応答えますが、SQLがこんなんだった場合、 SELECT COL1, COL2 …(省略) fetchで受け取る配列は$row[’COL1’]や$row[’COL2’]になりますってことです。
guest

1

記述方法が適正かどうかは置いておいて、

fetchAll()→該当する全てのデータを配列として返す

という意味みたいなんですが、
該当するデータなんて一件ぐらいしかないのになんで
わざわざ全てのデータを配列として返すfetchAllを使うんですか?

該当するデータが一件ではなくって複数件ある場合があるから、
その場合のデータの処理の仕方を記述しようとしているのだと思います。

例えば、
データベースには学年全員分のデータがあって、その中から3組の生徒だけ取得する
というようなケースの場合は数十人分の結果を取得するSQLを記述して、
その結果を全部扱いたいときに今回の様な記述が使えます。

投稿2017/03/13 14:55

tanat

総合スコア18703

marimokomokmOk👍を押しています

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

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

marimokomokmOk

2017/03/14 01:59

ご解答下さりありがとうございます。 ttyp03さんは、「ご指摘の通り、単なるfetchの方が適切かと思います。 」とおっしゃっています。 ログインとパスワードは、一つしか取得できないと思うんですが、もしかしたら2つ以上(同じログインとパスワード)を拾うことがありえるからfetchAllで全ての結果行を含む配列を返すのでしょうか?
guest

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

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

ただいまの回答率
85.53%

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

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

質問する

同じタグがついた質問を見る

PDO

PDO(PHP Data Objects)はPHPのデータベース抽象化レイヤーです。

PHP

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

データベース

データベースとは、データの集合体を指します。また、そのデータの集合体の共用を可能にするシステムの意味を含めます