I have a PHP 2D array, many keys, each with one value, I need to put this into a MySQL database.
The database has 8 fields. Eg. Field1, Field2, Field3, etc. I am trying to ensure value1 => field1, value2 =>field2, value3 => field3 and so on, when one record is full (i.e. after 8 values) a new record should be created for the next 8 values and so on.
I am aware that the 1st, 9th, 17th, 26th values etc, will need an insert statement and the intermediate values will be an update statement.
What is the best way of going about this?
array_chunk() is the possible answer if I took this question correct.
And then just something like this
foreach ($chunks as $row) {
array_map $row with mysql_real_escape_string
implode to get VALUES clause
INSERT
}
But the real array sample can save a ton of both your own and other people's time
Say, if you want to have saved the keys, not values, array_reverse must be called first.
Simplest to understand would be to use a counter. Like:
$cc=0;
while(...){ // Whatever your finished condition is
if($cc==0){
//INSERT
}else{
//UPDATE
}
$cc++;
if($cc==8) $cc=0;
}
$records = array_chunk($yourArray);
foreach($records as $record)
{
$record = array_map("mysql_real_escape_string", $record);
$q = 'INSERT INTO `yourTable` VALUES
'.$record[0].',
'.$record[1].',
'.$record[2].',
'.$record[3].',
'.$record[4].',
'.$record[5].',
'.$record[6].',
'.$record[7].',
';
$res = mysql_query($q);
}
I have a PHP 2D array, many keys, each with one value, I need to put this into a MySQL database.
Sounds very odd - PHP doesn't do 2-dimensional arrays. Only nested arrays.
I am aware that the 1st, 9th, 17th, 26th values etc, will need an insert statement
I presume that means that you don't have a 2D array - you've got a 2D data set mapped to a non-nested PHP array....in which case:
for ($x=0; $x<count($data)/8; $x+=8) {
$qry="INSERT INTO sometable (f1, f2, f3,f4,f5,f6,f7,f8) VALUES (";
$join='';
for ($y=0; $y<8; $y++ ) {
$qry.=$join . prep_val($data[$x+$y]);
$join=',';
}
mysql_query($qry);
}
(where prep_val enloses strings and escapes meta chars)
C.
I think you should keep in the db id of the last inserted row, and how many of the fields in this row are free.
This should allow you to make appropriate update and/or inserts when putting new data into db.
For splitting array into parts you may use array_slice() array_splice() and array_chunk() functions.
Related
I have an app that is receiving sensor data. As an illustration let's say the expected range is between 0.01 and 10. In this case in the migration I may have something like:
$table->float('example',5, 2)
This way I am able to handle an order of magnitude outside the expected range. However it is possible for the sensor to glitch and send values of say 10 000. As the sensor is sending an array of values it is likely that not all the data is incorrect so it is preferred to still write the data to the DB. For the initial insert I am using the code below which is working as expected:
DB::table($tableName)->insertOrIgnore($insert_array);
However, in some circumstances the sensor can resend the data in which case the record needs to be updated. It's possible that the value(s) that are out of range can remain in the array, in which case the update statement below will throw an out of range error:
DB::table($tableName)->where('$some_id','=', $another_id)->update($insert_array);
I have not been able to find an something akin to an "updateorignore" functionality. What is the best way to handle updating this record? Note I cannot simply put it in a try catch since this table will be a parent table to some children and ignoring it will result in some orphaned entries.
Do you have some unique points of data to tie the records together, such as a timestamp or an id from the origin of the data? If so, you can use updateOrInsert
DB::table($tableName)
->updateOrInsert(
['remote_id' => $insert_array['remote_id'],
[
'example_field_1' => $insert_array['example_field_1'],
'example_field_2' => $insert_array['example_field_2'],
]
);
This is discussed at:
https://laravel.com/docs/master/queries#updates
Thanks to James Clark Developer to help me get to the solution. Below is some sample code to resolve the problem:
$values = array();
//set up values for binding to prevent SQL injection
foreach ($insert_array as $item) {
$values[] = '?';
}
//array values need to be in a "flat array"
$flat_values = implode(", ", $values);
//add in separators ` to column names
$columns = implode("`, `",array_keys($insert_array));
//write sql statement
$sql = "INSERT IGNORE INTO `example_table` (`$columns`) VALUES
($flat_values) ON DUPLICATE KEY UPDATE id = '$id'";
DB::insert($sql, array_values($insert_array));
}
Following is my code showing some error in mysql query:
<?php
$con=mysql_connect('localhost','root','');
$str=$_GET["message"];
$stor=explode(" ",$str);// converting message into array
mysql_select_db('words',$con);
for($j=0;$j<=30; $j++)
{
mysql_query($con,"UPDATE blacklist SET $stor=1 where $stor=0");//if column name=element in array then make it as 1 in database
}
mysql_close($con);
?>
Your code is vulnerable to SQL Injection. Read up on prepared statements and use PDO/MySQLi.
$stor is an array object and cant be used directly in the query. If you want to use it, try using
IN('.implode(",", $stor).')
the code above does the following:
implode() - takes an array and turns it into a comma separated string.
IN() - compares the given comma separated values and returns true if at least one of them exists.
Example (implode):
implode(",", array(1,2,3)) IS EQUAL TO "1,2,3"
Example (IN):
TestID IN (1,2,3) IS SAME AS (TestID = 1 OR TestID = 2 OR TestID = 3)
You're probably getting a mysql error because your query ends up looking like this
UPDATE blacklist SET Array=1 where Array=0;
If you're just echoing out a full array, you get Array instead, you'll need to specify an array element ($stor[1] for example).
What you'll want to do is replace your for loop with a foreach so that you can just throw out the elements one at a time.
Also, your arguments are backwards.
foreach($stor as $word)
{
mysql_query("UPDATE blacklist SET $word=1 where $word=0", $con);
}
I am looking to use the contents of an array
$arr =array(24,28,30,34, 40);
and pass these into the where clause of a MySQL select statement, all my research has shown this done by using IN to pass in all the array values in one go.
I need to pass in each array element one at a time and then echo out the results of the SQL statement one at a time as the select statement is updated with the next array element.
New to programming and PHP so just need a little example to get me started...
Thanks to Zad highlighted the real issue
I need to pass each array value individually to a SQL statement as these need to be utilised in Where clause with BETWEEN, eg. WHERE age BETWEEN $array1 AND $array2 in order to determine count over an age range
thanks for all the input
You can use the implode function to build the string that contains the list;
$arr =array(24,28,30,34, 40);
$query = 'SELECT * FROM mytable WHERE id IN (' .implode($arr, ', '). ' )';
echo $query;`
http://codepad.org/tLPZxq8P
http://mx2.php.net/manual/en/function.implode.php
try it with escaping the argument
foreach($arr as $array_element) {
$query = 'SELECT * FROM table WHERE field = \''.mysql_real_escape_string($array_element).'\'';
//your statement
}
You can use a foreach function:
// make connection to mysql server
foreach ( $arr as $element ) {
$statement = "SELECT whatever FROM wherever WHERE something = $element"; // maybe a little validation here wouldn't hurt either
// execute statement
// process results
} // end of foreach
// close connection
$arr =array(24,28,30,34, 40);
$a = 'SELECT * FROM foo WHERE bar IN('.implode(',',$arr).')';
Edit: I'll admit, I didn't fully read the question, the title is misleading - consider changing that.
I need to pass in each array element one at a time and then echo out
the results of the SQL statement one at a time as the select statement
is updated with the next array element.
Could you explain how the scenario a bit better?
How can I add a value into an array in a database row, and then later on, when I want to get values of the array, simply display each different array value on a new line?
Also, how do arrays work in mysql and how to get the value of it?
Filed testField has serialized data.
$arrayData = array('one','two','three');
$serializedData = serialize($arrayData);
Mysql insertion:
insert INTO table ('testField') Values ($serializedData);
To get data:
select testField from table where id=1
You are getting here some string value. Then you should unserialize this string to get array:
$arrayData = unserialize($selectResultValue);
Look here for more details about serialize function:
http://php.net/manual/en/function.unserialize.php
MySQL does not have a native array data type. So, your first step is to figure out how you will store the elements of the array in a MySQL table.
Will you store each array element in its own database row?
elem val
1 value1
2 value2
...
n valuen
Or will you store the arraw as a series of concatenated values in a single row, something like this?
values
value1,value2,value3,...,valuen
In the first case, you can update a single array element easily:
UPDATE array SET val=newValue
WHERE elem=updatedElement
In the second case, you'll have to read the values column, break it out (deserialize it) into an array, change the element or elements you want to change, then gather it up (serialize it) back into a values column, and update your mySQL table. #Anthony pointed this out.
You need to answer the question about how you're storing the array before you can start to figure out how you will update it.
save array
$foo = array(1,2,3);
mysql_query(sprintf("INSERT INTO some_table ('foo') VALUES ('%s')", serialize($foo));
foo will appear as a string 1,2,3 in the database now
fetch array
$result = mysql_query("SELECT id, foo FROM some_table")
$item = mysql_fetch_object($result);
$foo = $item->foo;
$foo = unserialize($foo);
add data to array
$foo[] = 4;
$foo = array_uniq($foo); // you might want to ensure only unique values
mysql_query(sprintf("UPDATE some_table SET foo='%s' WHERE id=%d", serialize($foo), $item->id);
foo will appear as a string 1,2,3,4 in the database now
I am trying to insert an unknown number of rows into MySQL using PHP. This is how it should work:
Javascript parses HTML DOM to create a multi-dimensional array based on a css class. The array will have a certain number of rows(or sub-arrays) corresponding to the number of elements that have that class. (This could be any integer 0 or greater... obviously).
Then, on a JavaScript event, the array is sent to a PHP script.
The PHP script will INSERT data from the array into MySQL.
My problem is that I don't know how to tell my PHP script how many values are in the array. And I don't know how to write the mysql_query() without knowing the number of values (or rows) that should be inserted.
You can insert more than one row at a time to MySQL:
INSERT INTO table1 (column1, column2, ...) VALUES (value_col1, value_col2), (value2_col1, value2_col2), ...;
In PHP, you can build your query by looping through rows and adding them to the SQL string:
$sql = "INSERT INTO table1 (col1, col2) VALUES ";
foreach($rows as $i=>$row) {
if ($i>0) {
$sql .= sprintf(",(%s,%s)", $row["col1_value"], $row["col2_value"]);
} else {
$sql .= sprintf("(%s,%s)", $row["col1_value"], $row["col2_value"]);
}
}
mysql_query($sql);
You have to be sure to properly escape your values depending upon what you're actually inserting.
Why don't you prepare a two dimensional array while searching with the css class identifier like this?
//This is jquery code - you can write javascript to do the same
$(`.class`).each(function(i,e){resultsArray.push($(this).val());});
This will save you from the headache of traversing a multidimensional array in the backend and you can simply do a count() in you PHP code and the following query preparation.
Query preparation
Assuming you have a two dimensional array you can use a bulk insert query like this:-
INSERT INTO tablename (a,b)
VALUES
('1', 'one'),
('2', 'two'),
('3', 'three')
And prepare the query dynamically using PHP like this -
$counter = 0;
$valuesPart = NULL;
foreach($_POST as $each)
{
if($counter > 0)
$appendComma = ",";
else
$appendComma ="";
$valuesPart .= $appendComma."(".$each['key1'].",".$each['key2'].")";
$counter++;
}
if(!empty($valuesPart))
$mysql_query = "INSERT INTO tablename (a,b) VALUES ".$valuesPart;
So, you don't need to know how many results are to be actually inserted.
If you stay with the multidimensional array, you will probably need to code or search for a code to traverse the multidimensional array which will probably involve recursion and a lot of complex code. There will be many chances of errors and it will be a slower (may be little but a finite amount which is not necessary).
So I assume the array is getting to PHP successfully, through $_POST or whatever? If you aren't sure then do a var_dump or echo_r so we can see.
EDIT - wow I put explode where I meant implode several times. fixed.
Assuming that it is, and that each 'sub' array is an associative array in form
[0]
'id' => 1
'name' => 'Billy'
'DOB' => .....
[1]
etc.
And the code to build a single query inserting all rows, like this INSERT INTO table ('f1','f2',f3') VALUES ('v11', 'v22', 'v33'), ('v21', 'v22', 'v23'), ......
$escapeAndQuote = function($x) {return "'".mysql_real_escape_string($x)."'";};
$rowwise = function($x) {return '('. implode(', ', array_map($escapeAndQuote, $x)) .')';
$fieldString = $rowwise(array_keys($arr[0]));
$valString = implode(', ', array_map($rowwise, $arr));
$sql = "INSERT INTO table $fieldString VALUES $valString";
mysql_query($sql, $conn);
Use a foreach loop to cycle through the array.
// Example:
foreach($submitted_array as $insert_array)
{
//php and mysql insert query here
}
Perhaps prepared statements would assist you in your endeavors. Essentially you will declare a generic insert statement and then "bind" values to each input. Read more on PHP PDO Prepared Statements.