Other ways to add element in an array? - php

$a = ['foo' => 'bar'];
If I want to add new elements in this array I would usually write this
$a['foo2'] = 'bar2';
$a['foo3'] = 'bar3';
$a['foo4'] = 'bar4';
Is there some other syntax so I can add elements like this without overwriting $a?
$a = [ 'foo2' => 'bar2',
'foo3' => 'bar3',
'foo4' => 'bar4'];

You can also do something like this:
$arr1 = array('foo2' => 'bar2');
$arr2 = array('foo3' => 'bar3');
$arr3 = $arr1 + $arr2;

You can use array_merge to add an array to the end of another array.
$a = array_merge($a, $b);
where $b is:
$b = [ 'foo2' => 'bar2',
'foo3' => 'bar3',
'foo4' => 'bar4'];

Or just do:
$a = ['foo' => 'bar'];
$a = array_merge([$a,'foo2' => 'bar2',
'foo3' => 'bar3',
'foo4' => 'bar4'];
Will return what you want.

You could create a simple Function for that like so:
<?php
/**
* #param $mainArray => THE ARRAY TO WHICH OTHER ELEMENTS (INCL. ARRAYS/OBJECTS) SHOULD BE ADDED
* #param $data => A KEY-VALUE PAIR ARRAY OR A NORMAL STRING/NUMBER
* #return array
*/
function arrayAdd(&$mainArray, $data){
if(is_array($data)){
foreach($data as $k=>$v){
$mainArray[$k] = $v;
}
}else if(is_string($data)){
$mainArray[] = $data;
}
return $mainArray;
}
// CREATE A OBJECT (TO SHOW IT COULD ALSO HANDLE THAT AS WELL)
$obj = new stdClass();
$obj->name = 'Some Name';
$obj->tel = '+1 202 532 00 00 00';
// THE MAIN ARRAY TO WHICH OTHER ELEMENTS SHOULD BE ADDED
$main = ['foo1' => 'bar1', 'foo2' => 'bar2'];
// A COLLECTION OF DATA TO ADD TO $main
$data = [
'one' => 'Un',
'two' => 'Deux',
'three' => 'Trois',
'four' => 'Quart',
'obj' => $obj,
];
// CALL THE FUNCTION AND PASS THE PARAMETERS
var_dump( arrayAdd($main, $data) );
// YIELDS::
array (size=7)
'foo1' => string 'bar1' (length=4)
'foo2' => string 'bar2' (length=4)
'one' => string 'Un' (length=2)
'two' => string 'Deux' (length=4)
'three' => string 'Trois' (length=5)
'four' => string 'Quart' (length=5)
'obj' =>
object(stdClass)[1]
public 'name' => string 'Some Name' (length=9)
public 'tel' => string '+1 202 532 00 00 00' (length=19)

How about this ?
I think it is simplest to add element into an array
<?php
$cart = [];
//to add one
array_push($cart, 13);
// to add multiple
array_push($cart, 13,14,15);
?>

Related

real_escape_string on multidimensional array

I'm trying to escape values from a multidimensional array for my database class. The code I have currently:
// Function to escape array values
private function esc_sql_arr(array $to_esc) {
$clean_arr = array();
foreach($to_esc as $k => $v) {
if(is_array($to_esc[$k])) {
foreach($to_esc[$k] as $key => $val) {
$k = $this->_mysqli->real_escape_string($k);
$key = $this->_mysqli->real_escape_string($key);
$val = $this->_mysqli->real_escape_string($val);
$clean_arr[$k][$key] = $val;
}
} else {
$k = $this->_mysqli->real_escape_string($k);
$v = $this->_mysqli->real_escape_string($v);
$clean_arr[$k] = $v;
}
}
return $clean_arr;
}
I'm assuming the following input example (it should be 'where', I purposely changed it to test the above method):
$args = array(
"table" => "t'1",
"data" => array(
"c'sf4;(" => 'xdfbxdrf',
'c2' => "'t'est'",
'cs' => 'hey'
),
"whe're" => array(
'test' => 'test1'
)
);
var_dump:
array (size=3)
'table' => string 't\'1' (length=4)
'data' =>
array (size=3)
'c\'sf4;(' => string 'xdfbxdrf' (length=8)
'c2' => string '\'t\'est\'' (length=10)
'cs' => string 'hey' (length=3)
'whe\'re' =>
array (size=1)
'test' => string 'test1' (length=5)
The code works without any issue. However, is this the right way to escape a multidimensional array?
I believe I might not have to use this method since I use prepared statements. Any feedback on using this is welcome.

PHP Array Create from given Array

Thsi is my array structure.
$arr = array(
'Tablet'=>array('test1','test2'),
'Medicine'=>array('abc1'.'abc2'),
'Dosage'=>array('1','1'),
'Mode'=>array('testmode1','testmodel2'),
'Since'=>array('mng','mng')
);
I want to create an array like this.
array
0 =>
array
'Tablet' => string 'test1' (length=5)
'Medicine' => string 'abc1' (length=4)
'Dosage' => string '1' (length=1)
'Mode' => string 'testmode1' (length=9)
'Since' => string 'mng' (length=3)
1 =>
array
'Tablet' => string 'test2' (length=5)
'Medicine' => string 'abc1' (length=4)
'Dosage' => string '1' (length=1)
'Mode' => string 'testmode2' (length=9)
'Since' => string 'mng' (length=3)
Can someone pls help?
Sorry for bad english.
Thanks
$new = [];
foreach ($arr as $key => $sub) {
$i = 0;
foreach ($sub as $value) {
$new[$i][$key] = $value;
$i++;
}
}
That should do the trick :)
$newArr = array();
foreach ( $arr as $key => $subArr ){
for ($i= 0; $i < count($subArr); $i++){
if (!array_key_exists($i, $newArr)){
$newArr[$i] = array();
}
$newArr[$i][$key] = $subArr[$i];
}
}
$arr = array(
'Tablet'=>array('test1','test2'),
'Medicine'=>array('abc1','abc2'),
'Dosage'=>array('1','1'),
'Mode'=>array('testmode1','testmodel2'),
'Since'=>array('mng','mng')
);
$na=array();
foreach($arr as $k=>$v){
foreach($v as $kk=>$vv){
$na[$kk][$k]=$vv;
}
}
echo "<pre>";print_r($na);
Easy you can append each one to normal array like this
$arr1 = array(
'Tablet'=>array('test1','test2'),
'Medicine'=>array('abc1'.'abc2'),
'Dosage'=>array('1','1'),
'Mode'=>array('testmode1','testmodel2'),
'Since'=>array('mng','mng')
);
$arr2 = array(
'Tablet'=>array('test1','test2'),
'Medicine'=>array('abc1'.'abc2'),
'Dosage'=>array('1','1'),
'Mode'=>array('testmode1','testmodel2'),
'Since'=>array('mng','mng')
);
$arr3 = array(
'Tablet'=>array('test1','test2'),
'Medicine'=>array('abc1'.'abc2'),
'Dosage'=>array('1','1'),
'Mode'=>array('testmode1','testmodel2'),
'Since'=>array('mng','mng')
);
$a=array();
array_push($a,arr1,arr2,arr3);
print_r($a);
output will look
array
0 =>
array
'Tablet' => string 'test1' (length=5)
'Medicine' => string 'abc1' (length=4)
'Dosage' => string '1' (length=1)
'Mode' => string 'testmode1' (length=9)
'Since' => string 'mng' (length=3)
1 =>
array
'Tablet' => string 'test2' (length=5)
'Medicine' => string 'abc1' (length=4)
'Dosage' => string '1' (length=1)
'Mode' => string 'testmode2' (length=9)
'Since' => string 'mng' (length=3)
$myLength = count($arr['Tablet'])
$newArray = array();
for (i=0; i < $myLength ; i++)
{
$newArray[i]['Tablet'] = $arr['Tablet'][i];
$newArray[i]['Medicine'] = $arr['Medicine'][i];
$newArray[i]['Dosage'] = $arr['Dosage'][i];
$newArray[i]['Mode'] = $arr['Mode'][i];
$newArray[i]['Since'] = $arr['Since'][i];
}
What do you meant adding the (lentgh = x) in your question?

How to create nested object in PHP

$array = (object)array(
'name' => 'David',
'friends' => (object)array(
(object)array('name' => 'Max'),
(object)array('name' => 'Jian')
)
);
var_dump($array);
I want to learn how to use stdClass function to get the same result, don't want to use (object) before each array, convert cause some resource, and I know json_encode and json_decode can make it, just want to learn how stdClass make nested structure.
There's a trick with json_encode() to easily get this:
$array = array(
'foo' => array('bar'=>'a', 'baz'=>'b'),
'feo' => 'bee',
'boo' => array('a'=>array('x', 'y'), 'b'=>array('z'))
);
$object = json_decode(json_encode($array));
Update
If you don't want to use JSON function, you can handle your array recursively, like:
function getStdObject(array $data)
{
foreach($data as &$item)
{
if(is_array($item))
{
$item = getStdObject($item);
}
}
return (object)$data;
}
$array = array(
'foo' => array('bar'=>'a', 'baz'=>'b'),
'feo' => 'bee',
'boo' => array('a'=>array('x', 'y'), 'b'=>array('z'))
);
$object = getStdObject($array));
This class is available at: http://php.net/manual/en/arrayobject.construct.php#111192
/**
* #author Iltar van der Berg
* #version 2.0.0
*/
class RecursiveArrayObject extends ArrayObject
{
/**
* overwrites the ArrayObject constructor for
* iteration through the "array". When the item
* is an array, it creates another self() instead
* of an array
*
* #param Array $array data array
*/
public function __construct(Array $array)
{
foreach($array as $key => $value) {
if(is_array($value)){
$value = new static($value);
}
$this->offsetSet($key, $value);
}
}
/**
* returns Array when printed (like "echo array();")
* instead of an error
*
* #return string
*/
public function __ToString()
{
return 'Array';
}
}
Usage:
$a = array(
'one' => array(
'hello','world'
),
'two' => array(
'lorem','ipsum'
)
);
var_dump($a);
$o = new RecursiveArrayObject($a);
var_dump($o);
Yields:
array (size=2)
'one' =>
array (size=2)
0 => string 'hello' (length=5)
1 => string 'world' (length=5)
'two' =>
array (size=2)
0 => string 'lorem' (length=5)
1 => string 'ipsum' (length=5)
object(RecursiveArrayObject)[1]
public 'one' =>
object(RecursiveArrayObject)[2]
string 'hello' (length=5)
string 'world' (length=5)
public 'two' =>
object(RecursiveArrayObject)[3]
string 'lorem' (length=5)
string 'ipsum' (length=5)

Unique PHP Array

How can I check if the values are unique in an array based on the key value? Below is the out put of the array. I want to remove duplicate values based on the "id" key. If you check below, the 2nd & 3rd array are same except for the "role" value. Because of this, array_unique is not working on this array.
array
0 =>
array
'id' => string '1521422' (length=7)
'name' => string 'David Alvarado' (length=14)
'role' => string 'associate producer ' (length=20)
1 =>
array
'id' => string '0098210' (length=7)
'name' => string 'Cristian Bostanescu' (length=19)
'role' => string 'line producer: Romania (as Cristi Bostanescu)' (length=46)
2 =>
array
'id' => string '1266015' (length=7)
'name' => string 'Bruno Hoefler' (length=13)
'role' => string 'co-producer ' (length=13)
3 =>
array
'id' => string '1266015' (length=7)
'name' => string 'Bruno Hoefler' (length=13)
'role' => string 'executive producer ' (length=20)
4 =>
array
'id' => string '1672379' (length=7)
'name' => string 'Alwyn Kushner' (length=13)
'role' => string 'associate producer ' (length=20)
Try this one:
<?php
$array = array(
array('id' => 1, 'text' => 'a'),
array('id' => 2, 'text' => 'b'),
array('id' => 1, 'text' => 'c'),
array('id' => 3, 'text' => 'd')
);
$array = array_filter($array, function ($item) {
static $found = array();
if (isset($found[$item['id']])) return false;
$found[$item['id']] = true;
return true;
});
var_dump($array);
This works as of PHP 5.3 (because of the closure and static statement).
cf. http://php.net/manual/en/function.array-filter.php for more information. I tested the statement within loops, it works there as well.
Basically you want to implement a variation of array_unique that does what you want:
function array_unique_multi($arr,$key='id') {
// $arr is the array to work on
// $key is the key to make unique by
$ret = Array();
foreach($arr as $v) {
if( !isset($ret[$v[$key]])) $ret[$v[$key]] = $k;
}
return array_values($ret);
}
You can use this code:
// assuming $arr is your original array
$narr = array();
foreach($arr as $key => $value) {
//$narr[json_encode($value)] = $key;
if (!array_key_exists($value["id"], $narr))
$narr[$value["id"]] = $key;
}
$narr = array_flip($narr);
foreach($arr as $key => $value) {
if (!array_key_exists($key, $narr))
unset($arr[$key]);
}
print_r($arr); // will have no duplicates

PHP Question: how to array_intersect_assoc() recursively

Let's say I want to do this:
$a = array_intersect_assoc(
array(
'key1' => array(
'key2' => 'value2'
),
'key3' => 'value3',
'key4' => 'value4'
),
array(
'key1' => array(
'key2' => 'some value not in the first parameter'
),
'key3' => 'another value'
)
);
var_dump( $a );
The printed result is:
array
'key1' =>
array
'key2' => string 'value2' (length=6)
It's clear that values associated with 'key2' in both arrays are not the same, however array_intersect_assoc() still return 'key2' => 'value2' as the intersected value.
Is this the expected behavior of array_intersect_assoc()?
Thanks!
Yes, it's the expected behavior, because the comparison is done using string representations, and the function does not recurse down nested arrays. From the manual:
The two values from the key => value pairs are considered equal only if (string) $elem1 === (string) $elem2 . In other words a strict type check is executed so the string representation must be the same.
If you tried to intersect with an array with 'key1' => 'Array', you'd get the same result because the string representation of an array is always 'Array'.
One of the user-contributed notes, by nleippe, contains a recursive implementation that looks promising (I modified the third line to do string comparison on any non-array values):
function array_intersect_assoc_recursive(&$arr1, &$arr2) {
if (!is_array($arr1) || !is_array($arr2)) {
// return $arr1 == $arr2; // Original line
return (string) $arr1 == (string) $arr2;
}
$commonkeys = array_intersect(array_keys($arr1), array_keys($arr2));
$ret = array();
foreach ($commonkeys as $key) {
$ret[$key] =& array_intersect_assoc_recursive($arr1[$key], $arr2[$key]);
}
return $ret;
}
function array_key_match_recursive(array $main, array $other, $i = 0, &$result = []) {
foreach($main as $key => $value) {
$k = sprintf('%s%s', str_repeat('=', $i), $key);
if (!isset($other[$key])) {
$result[$k][] = 'not key';
}
if (!is_array($value) && empty($other[$key])) {
$result[$k][] = 'value empty';
}
if (is_array($value) && isset($other[$key])) {
array_key_match_recursive($value, $other[$key], ++$i, $result);
}
}
//return (bool) !$result;
return $result;
}
A function that does what you need:
/**
* Get array intersect assoc recursive.
*
* #param mixed $value1
* #param mixed $value2
*
* #return array|bool
*/
function getArrayIntersectAssocRecursive(&$value1, &$value2)
{
if (!is_array($value1) || !is_array($value1)) {
return $value1 === $value2;
}
$intersectKeys = array_intersect(array_keys($value1), array_keys($value2));
$intersectValues = [];
foreach ($intersectKeys as $key) {
if (getArrayIntersectAssocRecursive($value1[$key], $value2[$key])) {
$intersectValues[$key] = $value1[$key];
}
}
return $intersectValues;
}
My version based on #BoltClock version:
function array_intersect_assoc_recursive($arr1, $arr2) {
if (!is_array($arr1) || !is_array($arr2)) {
return $arr1;
}
$commonkeys = array_keys($arr1);
if (!array_key_exists('$', $arr2)){
$commonkeys = array_intersect(array_keys($arr1), array_keys($arr2));
}
$ret = array();
foreach ($commonkeys as $key) {
$ret[$key] = array_intersect_assoc_recursive($arr1[$key], array_key_exists('$', $arr2) ? $arr2['$'] : $arr2[$key]);
}
return $ret;
}
I use this code to filter data inside complex array
example:
$filter = [
'channels' => [
'$' => [
'id' => 1,
'type' => 1,
'count' => 1
]
],
'user' => [
'id' => 1,
'type' => 1
]
];
$data = [
'user' => [
'id' => '1234',
'type' => true,
'counter' => 14,
],
'filteredField' => 4,
'channels' => [
['id' => '567', 'type' => 'other', 'count' => 1345, 'filteredField' => 5,],
['id' => '890', 'type' => 'other', 'count' => 5456, 'filteredField' => 7,],
],
];
print_r(array_intersect_assoc_recursive($data, $filter));
test online:
https://onlinephp.io/c/3be04

Categories