I have a simple user table with columns: username, password, email, name, surname, birthdate, address and city. the first three are mandatory but the rest of them can be null.
I am connecting to the database and fetch rows in an array and print it.
$dbc=mysqli_connect(DB_HOST, DB_USER, DB_PASSWORD, DB_NAME);
$sql = "select * from user";
$data = mysqli_query($dbc, $sql) or die("query exec error");
//$json = array();
if(mysqli_num_rows($data)){
while($row=mysqli_fetch_array($data)){
//$json['Kullanici'][]=$row;
print_r($row);
echo "<br /><br />";
}
}
mysqli_close($dbc);
//echo json_encode($json);
But the output is like this:
Array ( [0] => ayse [username] => ayse [1] => b1b3773a05c0ed0176787a4f1574ff0075f7521e [password] => b1b3773a05c0ed0176787a4f1574ff0075f7521e [2] => ayse#hotmail.com [email] => ayse#hotmail.com [3] => [name] => [4] => [surname] => [5] => 0000-00-00 [birthdate] => 0000-00-00 [6] => [address] => [7] => istanbul [city] => istanbul )
Array ( [0] => baris [username] => baris [1] => 7c4a8d09ca3762af61e59520943dc26494f8941b [password] => 7c4a8d09ca3762af61e59520943dc26494f8941b [2] => bakkurt#hotmail.com [email] => bakkurt#hotmail.com [3] => Barış [name] => Barış [4] => [surname] => [5] => 0000-00-00 [birthdate] => 0000-00-00 [6] => [address] => [7] => [city] => )
The question is why there is both [0]=>baris and [username] => baris. I was expecting only the username=>baris. Was I wrong? Where am i missing?
If i solve this problem, I will convert the array to json by removing comments.
It's not a problem, if you look at the PHP documentation for the mysqli_fetch_array() function, it accepts a parameter resulttype; it determines whether to return records as arrays with numeric indices alone, associative indices alone or both (which is what you have).
By default, the function uses MYSQLI_BOTH.
To get as numeric indices alone:
while($row=mysqli_fetch_array($data, MYSQLI_NUM)){
//this will always return with numeric indices alone
}
For more information check here PHP mysqli_fetch_array
if you need only username => baris
Try mysqli_fetch_assoc.
Courtesy - http://www.php.net
It returns an associative array of strings representing the fetched row
in the result set, where each key in the array represents the name of
one of the result set's columns or NULL if there are no more rows in
resultset.
I think what you are looking for is the resulttype parameter. Have a look at this page: mysqli_result::fetch_array
You probably want to call the fetch_array function like this:
mysqli_fetch_array($data, MYSQLI_ASSOC)
Try using mysqli_fetch_assoc() instead of mysqli_fetch_array().
mysqli_fetch_array() fetch data as both enumerated and associative, so if you only need associative array use mysqli_fetch_array().
You can also read the documentation if you want to know something more about it.
Related
I'm trying to make sense of the JSON output and I was hoping someone here might be kind enough to walk me through it as it's been a while since I used JSON.
I have the following PHP
$Query01 = "SELECT `Department`,`DepartmentHeadID` FROM `Department`";
$Result01 = mysql_query($Query01) or die("Error 01: " . mysql_error());
while($r = mysql_fetch_array($Result01))
{
// Create JSON Data:
$rows[] = $r;
}
// echo json_encode($rows);
$Data = json_encode($rows);
echo '<pre>';
print_r(json_decode($Data));
echo '</pre>';
Which generates the following:
Array
(
[0] => stdClass Object
(
[0] => Despatch
[Department] => Despatch
[1] => 1
[DepartmentHeadID] => 1
)
[1] => stdClass Object
(
[0] => Factory
[Department] => Factory
[1] => 2
[DepartmentHeadID] => 2
)
[2] => stdClass Object
(
[0] => Finishing
[Department] => Finishing
[1] => 3
[DepartmentHeadID] => 3
)
[3] => stdClass Object
(
[0] => Accounts
[Department] => Accounts
[1] => 8
[DepartmentHeadID] => 8
)
[4] => stdClass Object
(
[0] => Reps
[Department] => Reps
[1] => 13
[DepartmentHeadID] => 13
)
All I was expecting was the column Department & DepartmentHeadID
Would really appreciate understanding this output a little more.
Any thoughts...?
You actually missed that part in the documentation of array mysql_fetch_array ( resource $result [, int $result_type = MYSQL_BOTH ] )
result_type
The type of array that is to be fetched. It's a constant and can take the following values: MYSQL_ASSOC, MYSQL_NUM, and MYSQL_BOTH.
The type of returned array depends on how result_type is defined. By using MYSQL_BOTH (default), you'll get an array with both associative and number indices.
source : http://php.net/manual/en/function.mysql-fetch-array.php
Since MYSQL_BOTH is the default value for $result_type when you do not pass the second parameter to mysql_fetch_array, you end up with both the number and associative indices in your array.
So if you only want Department & DepartmentHeadID, you should go by
$r = mysql_fetch_array($Result01, MYSQL_ASSOC)
Using MYSQL_ASSOC, you only get associative indices (as mysql_fetch_assoc() works)
Bottom line : I would also recommend to prepare yourself to the deprecation of mysql_* functions as you can clearly see it stated in the official documentation linked here above and that you get information about PDO
A good starting point may be this question : Why shouldn't I use mysql_* functions in PHP?
Trying to get some database results in a very simple application.
Code
$pdo = new PDO("mysql:host=localhost;dbname=soundinsider", "root", "");
$pdo->setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION);
$sql = "SELECT * FROM users";
$query = $pdo->query($sql);
echo '<pre>';
print_r($query->fetchAll());
And this is what's output
Array
(
[0] => Array
(
[user_id] => 1
[0] => 1
[username] => simon
[1] => simon
[email] => madeup
[2] => madeup
)
[1] => Array
(
[user_id] => 2
[0] => 2
[username] => bobwin
[1] => bobwin
[email] => fake#email.com
[2] => fake#email.com
)
)
So there seems to be an extra key created for each result. This wasn't the case when I was coding a month or two ago. Is there something wrong here or is this now PDO behaviour?
this is configurable behavior:
$statement->fetchAll(PDO::FETCH_ASSOC)
will return associative arrays -- see argument $fetch_style.
you can configure your pdo instance to always do this:
$pdo->setAttribute(PDO::ATTR_DEFAULT_FETCH_MODE, PDO::FETCH_ASSOC);
there also is PDOStatement::setFetchMode() which is useful when using repeated prepared statements.
If you have a look at the manual, you'll see that fetchAll defaults to returning both an associate index and a numeric index - I'd suggest you use fetch instead and set associate return.
I want to store the contents of a specific database into an array, grouped by their primary keys. (Instead of the useless way PDO fetchAll() organises them).
My current code:
$DownloadsPDO = $database->dbh->prepare("SELECT * FROM `downloads`");
$DownloadsArray = $DownloadsPDO->execute();
$DownloadsArray = $DownloadsPDO->fetchAll();
Which then outputs:
Array ( [0] => Array ( [id] => 0 [0] => 0 [path] => /xx-xx/testfile.zip [1] => /xx-xx/testfile.zip [name] => Test Script [2] => Test Script [status] => 1 [3] => 1 ) [1] => Array ( [id] => 1 [0] => 1 [path] => /xx-xx/test--file.zip [1] => /xxxx/testfile.zip [name] => New Script-UPDATE [2] => New Script-UPDATE [status] => 1 [3] => 1 ) )
I was considering to use PDO::FETCH_PAIR, however I will be very soon expanding the amount of data I want to be able to use on this script. This works currently, but when I start to expand the amount of downloads and more clients come into play, obviously the way the data is grouped causes an issue.
Is it possible for me to group each array by their primary key (which is id)?
You can just use
$results = array_map('reset', $stmt->fetchAll(PDO::FETCH_GROUP|PDO::FETCH_ASSOC))
PDO::FETCH_GROUP|PDO::FETCH_ASSOC returns an array of arrays. The first column is used as the key, and then within key is an array of all the results for that key. However, in our scenario each key will only contain 1 row. reset() returns the first element in array, thus eliminating 1 level of nesting.
This should yield what you are looking for :
$results = $pdos->fetchAll(\PDO::FETCH_UNIQUE|\PDO::FETCH_ASSOC);
I decided to just loop through the results with fetch() and enter them into an array as I go along, this is the code I have used and it works just fine:
$DownloadsPDO = $database->dbh->query("SELECT * FROM `downloads`");
$Array = array();
while ($d = $DownloadsPDO->fetch()) {
$Array[$d['id']]["id"] = $d['id'];
$Array[$d['id']]["name"] = $d['name'];
$Array[$d['id']]["path"] = $d['path'];
}
// Outputs
Array ( [1] => Array ( [id] => 1 [name] => Test Script [path] => /xxxx/testfile.zip ) [2] => Array ( [id] => 2 [name] => New Script-UPDATE [path] => /xxxx/testfile.zip ) )
Which uses the primary key (being id) as the name for the array key, and then adds the data into it.
Thought I would add this as the answer as this solved it, thanks to the guys that helped out and I hope this is helpful to anyone else hoping to achieve the same thing.
I'd like to point out the only solution that works for me:
fetchAll(\PDO::FETCH_GROUP|\PDO::FETCH_UNIQUE|\PDO::FETCH_ASSOC);
Beware that this will strip the first column from the resultset. So the query must be:
SELECT id_keyname AS arrkey, id_keyname, .... FROM ...
I'm still suggesting you to loop using fetch() method. Otherwise, you can use array_reduce() to iterate over the array. A sample on codepad is here.
The code(in human readable form) will be:
$myFinalArray = array_reduce($myInputArray, function($returnArray, $temp) {
$temp2 = $temp['id'];
unset($temp['id']);
$returnArray[$temp2] = $temp;
return $returnArray;
}
);
So, my question is; is it possible for me to group each array by their
primary key (which is id)
Off course, you have 2 options here: Either to change the query or parse a result-set.
So, I'm sure you don't want to change query itself, so I'd go with parsing result-set.
Note:
You should use prepared SQL statements when they make sense. If you want to bind some parameters then its OKAY. But in this case, you only want get get result-set, so prepare() and fetch() will be kinda overdo.
So, you have:
Array ( [0] => Array ( [id] => 0 [0] => 0 [path] => /xx-xx/testfile.zip [1] => /xx-xx/testfile.zip [name] => Test Script [2] => Test Script [status] => 1 [3] => 1 ) [1] => Array ( [id] => 1 [0] => 1 [path] => /xx-xx/test--file.zip [1] => /xxxx/testfile.zip [name] => New Script-UPDATE [2] => New Script-UPDATE [status] => 1 [3] => 1 ) )
And you want:
Array( [id] => Array('bar' => 'foo') ....)
Well, you can do something like this:
$stmt = $database->dbh->query("SELECT * FROM `downloads`");
$result = array();
foreach($stmt as $array){
$result[$array['id']] = $array;
}
print_r($result); // Outputs: Array(Array('id' => Array(...)))
I have a php script does this:
Put UPC into form
Submit form
Check to see if the UPC already exists in my database
If yes, fetch it from MySQL database
If not, fetch it from an external server, add it to MySQL database for future use
Display results
It works fine, but I'd like the variable to look exactly the same wether it comes from the MySQL cache, or the external server.
When I print it from the server, it looks like this:
Output:
[upc] => 066721020215
[pendingUpdates] => 0
[status] => success
[ean] => 0066721020215
[issuerCountryCode] => us
[found] => 1
[description] => Christie - Original Ritz Crackers
[message] => Database entry found
[size] => 225 g
[issuerCountry] => United States
[noCacheAfterUTC] => 2012-08-06T12:23:58
[lastModifiedUTC] => 2009-04-06T01:51:08
However, When I print the array from MySQL, it looks like this:
$result = mysql_query("SELECT * FROM UPC WHERE `upc` = '$codes[0]'");
$data = mysql_fetch_array($result);
echo "<pre>" . print_r($data, true) . "</pre>";
Output:
[0] => 066721020215
[upc] => 066721020215
[1] => 0
[pendingUpdates] => 0
[2] => success
[status] => success
[3] => 0066721020215
[ean] => 0066721020215
[4] => us
[issuerCountryCode] => us
[5] => 1
[found] => 1
[6] => Christie - Original Ritz Crackers
[description] => Christie - Original Ritz Crackers
[7] => Database entry found
[message] => Database entry found
[8] => 225 g
[size] => 225 g
[9] => United States
[issuerCountry] => United States
[10] => 2012-08-06
[noCacheAfterUTC] => 2012-08-06
[11] => 2009-04-06
[lastModifiedUTC] => 2009-04-06
I realize it's more or less a cosmetic difference (and an array twice as big as it needs to be), but how would I go about easily removing the 0,1,2,3,etc identifiers without looping through the array creating and manually creating a new one? Is there a function that would remove the numbered identifiers?
You need to use mysql_fetch_array($result, MYSQL_ASSOC) or mysql_fetch_assoc($result).
See http://php.net/manual/en/function.mysql-fetch-array.php and http://www.php.net/manual/en/function.mysql-fetch-assoc.php for more details.
Note that both are discouraged, as they have been replaced by the new(ish) mysqli functions: http://uk.php.net/manual/en/book.mysqli.php
Change the line:
$data = mysql_fetch_array($result);
to:
$data = mysql_fetch_assoc($result);
mysql_fetch_assoc returns the data from the db as an associative array - mysql_fetch_array returns a mixed array, with both numeric and associative indexes.
See http://php.net/manual/en/function.mysql-fetch-assoc.php
I've a problem with one of my function in PHP.
It returns the result two times with different keys…
I want the result only one time without the number keys.
This query and function returns the following array:
<?php
#The query
$typo = GetRowsParams("SELECT * FROM glyphs WHERE g_OK=1");
#The function
function GetRowsParams($requete, $params = array())
{
global $bdd;
$stmt = $bdd->prepare($requete) or die(print_r($req->errorinfo()));;
$stmt->execute($params);
$result = $stmt->fetchAll();
return $result;
}
?>
# The Array
Array (
[0] => Array (
[g_ID] => 1
[0] => 1
[g_name] => zero_Nagar.svg
[1] => zero_Nagar.svg
[g_height] => 1174
[2] => 1174
[g_width] => 352
[3] => 352
[g_tag] => Test
[4] => Test
[g_u_ID] => 2
[5] => 2
[g_path] => 02uploads/Test/zero_Nagar.svg
[6] => 02uploads/Test/zero_Nagar.svg
[g_path_PNG] => 02uploads/Test/zero_Nagar.png
[7] => 02uploads/Test/zero_Nagar.png
[g_OK] => 1
[8] => 1
)
[1] => Array (
[g_ID] => 2
[0] => 2
[g_name] => A
Nagar.svg [1] => A
…
…
Why each row is displayed twice with a different key? Where is my mistake?
Thank you for your help…
it is because by default php returns an array where all data has a textual AND a numeric index.
To keep only the textual index, passe PDO::FETCH_ASSOC in the fechAll function like that :
stmt->fetchAll(PDO::FETCH_ASSOC);
Add the argument PDO::FETCH_ASSOC like so:
$result = $stmt->fetchAll(PDO::FETCH_ASSOC);
(You can see the different fetch styles here: http://www.php.net/manual/en/pdostatement.fetch.php)
Read up on the PDOStatement::fetch methods. The first argument is a "fetch style," which defaults to fetching an array that looks like the above. If you just want an array that maps field names to valuse, use:
$result = $bdd.fetchAll(PDO::FETCH_ASSOC);