missing bits
[mdref/mdref-pq] / pq / Result / : Fetching Results.md
1 # pq\Result: Overview
2
3 An synchronous pq\Connection::exec*() call, or calls to pq\Connection::getResult() after using [asynchronous queries](pq/Connection/: Asynchronous Usage) returns an instance of pq\Result on success. See [Query execution](pq/Connection/: Executing Queries), optionally with [types](pq/Types/: Overview) and [Prepared Statements](pq/Statement/: Overview) for details about how to execute queries.
4
5 ## Fetch types:
6
7 pq\Result supports the follwing fetch types:
8
9 * pq\Result::FETCH_ARRAY
10 Fetch the row as ***numerically indexed array***.
11 * pq\Result::FETCH_ASSOC
12 Fetch the row as ***associative array*** indexed by column name.
13 * pq\Result::FETCH_OBJECT
14 Fetch the row as stdClass ***object***.
15
16 The fetch type is inherited from pq\Connection::$defaultFetchType can be set through the ***public*** property named pq\Result::$fetchType, to be used when no fetch type is specified in the call to a fetch method.
17
18 ## Number of rows:
19
20 The number of rows can be obtained from the ***public readonly*** property pq\Result::$numRows, or passing the result instance, which implements the Countable interface, to the count() function.
21
22 ## Number of columns:
23
24 The number of columns each row has, can be obtained from the ***public readonly*** property pq\Result::$numCols.
25
26 ## Fetching everything as an array of rows:
27
28 pq\Result::fetchAll() fetches the complete result set as an array of arrays or objects, depending on the default fetch type, as explained above, or the ***fetch type*** passed as first argument to the method.
29
30 <?php
31
32 try {
33 $connection = new pq\Connection;
34
35 $result = $connection->exec("SELECT id, name, email FROM accounts WHERE email LIKE '_@%'");
36
37 foreach ($result->fetchAll(pq\Result::FETCH_OBJECT) as $row) {
38 echo "ID: {$row->id}\n";
39 echo "Name: {$row->name}\n";
40 echo "Mail: {$row->email}\n\n";
41 }
42 } catch (\pq\Exception $e) {
43 echo $e->getMessage(), "\n";
44 }
45
46 ?>
47
48 pq\Result implements the virtual Traversable interface, so the above task can also be accomplished by this code:
49
50 <?php
51
52 try {
53 $connection = new pq\Connection;
54 $connection->defaultFetchType = pq\Result::FETCH_OBJECT;
55
56 $result = $connection->exec("SELECT id, name, email FROM accounts WHERE email LIKE '_@%'");
57
58 foreach ($result as $row) {
59 echo "ID: {$row->id}\n";
60 echo "Name: {$row->name}\n";
61 echo "Mail: {$row->email}\n\n";
62 }
63 } catch (\pq\Exception $e) {
64 echo $e->getMessage(), "\n";
65 }
66
67 ?>
68
69 ## Iteratively fetching row by row:
70
71 pq\Result::fetchRow() will return FALSE when the end of the result set has been reached.
72
73 <?php
74
75 try {
76 $connection = new pq\Connection;
77
78 $result = $connection->exec("SELECT id, name, email FROM accounts WHERE email LIKE '_@%'");
79
80 while (list($id, $name, $email) = $result->fetchRow()) {
81 echo "ID: {$id}\n";
82 echo "Name: {$name}\n";
83 echo "Mail: {$email}\n\n";
84 }
85 } catch (\pq\Exception $e) {
86 echo $e->getMessage(), "\n";
87 }
88
89 ?>
90
91 As with most ```fetch*()``` methods, the fetch type can be passed as argument here, too.
92
93 ## Fetching a single column by row:
94
95 Because a column value can be NULL or FALSE, pq\Result::fetchCol() stores the ***value*** into the first argument ***passed by reference***. The demanded ***column index/name*** can be passed as second argument, where ***column indices start with 0***, which is also the default.
96
97 <?php
98
99 try {
100 $connection = new pq\Connection;
101
102 $result = $connection->exec("SELECT email FROM accounts WHERE email LIKE '_@%'");
103
104 while ($result->fetchCol($email)) {
105 echo "Mail: {$email}\n";
106 }
107 } catch (\pq\Exception $e) {
108 echo $e->getMessage(), "\n";
109 }
110
111 ?>
112
113 When the end of the result set has been reached, pq\Result::fetchCol() will return FALSE.
114
115 > ***NOTE:***
116 > pq\Result::fetchCol() does not accept a fetch type argument.
117
118 ## Fetching bound variables:
119
120 It is possible to bind variables to result columns by reference by calling pq\Result::bind() for each demanded column and then retreive the results by calling pq\Result::fetchBound() iteratively.
121
122 <?php
123
124 try {
125 $connection = new pq\Connection;
126
127 $result = $connection->exec("SELECT id, name, email FROM accounts WHERE email LIKE '_@%'");
128
129 $result->bind("id", $id);
130 $result->bind("name", $name);
131 $result->bind("email", $email);
132
133 while ($result->fetchBound()) {
134 echo "ID: {$id}\n";
135 echo "Name: {$name}\n";
136 echo "Mail: {$email}\n\n";
137 }
138 } catch (\pq\Exception $e) {
139 echo $e->getMessage(), "\n";
140 }
141
142 ?>
143
144
145 pq\Result::bind() expects the ***column index/name*** as first argument and the ***variable to bind by reference to this result column*** as second argument.
146
147 > ***NOTE:***
148 > pq\Result::fetchBound() does not accept a fetch type argument.
149
150 ## Fetching simple maps:
151
152 pq\Result::map() fetches the complete result set as a simple map, a ***multi dimensional array***, each dimension indexed by a column.
153
154 Consider the following example:
155
156 <?php
157
158 try {
159 $connection = new pq\Connection;
160
161 $result = $connection->exec("SELECT a,b,c from generate_series(1,3) a,
162 generate_series(4,6) b,
163 generate_series(7,9) c");
164
165 foreach($result->map(array(0,1,2)) as $a => $aa) {
166 foreach ($aa as $b => $bb) {
167 foreach ($bb as $c => $res) {
168 printf("%s,%s,%s = %s ", $a, $b, $c, implode(",", $res));
169 }
170 printf("\n");
171 }
172 printf("\n");
173 }
174 } catch (\pq\Exception $e) {
175 echo $e->getMessage(), "\n";
176 }
177
178 ?>
179
180
181 It should produce:
182
183 1,4,7 = 1,4,7 1,4,8 = 1,4,8 1,4,9 = 1,4,9
184 1,5,7 = 1,5,7 1,5,8 = 1,5,8 1,5,9 = 1,5,9
185 1,6,7 = 1,6,7 1,6,8 = 1,6,8 1,6,9 = 1,6,9
186
187 2,4,7 = 2,4,7 2,4,8 = 2,4,8 2,4,9 = 2,4,9 // This should help generate maps
188 2,5,7 = 2,5,7 2,5,8 = 2,5,8 2,5,9 = 2,5,9 // of f.e. statistical data with
189 2,6,7 = 2,6,7 2,6,8 = 2,6,8 2,6,9 = 2,6,9 // some GROUP BYs etc.
190
191 3,4,7 = 3,4,7 3,4,8 = 3,4,8 3,4,9 = 3,4,9
192 3,5,7 = 3,5,7 3,5,8 = 3,5,8 3,5,9 = 3,5,9
193 3,6,7 = 3,6,7 3,6,8 = 3,6,8 3,6,9 = 3,6,9
194
195 pq\Result::map() optionally expects an ***array containing the column indices/names used to index the map*** as first argument, and uses the first column (at index 0) by default. The second argument can optionally be an ***array of column indices/names*** which should build up the leaf entry of the map. A ***fetch type*** can also be specified as optional third argument.