Using variable to access multidimensional $_POST - php

Consider this code:
$var = 'test';
$_POST[$test]; // equals $_POST['test']
How can I access with the same method this variable:
$_POST['test'][0];
$var = 'test[0]'; clearly doesn't work.
EDIT
Let me give a bit more information. I've got a class that builds a form.
An element is added like this:
//$form->set_element(type, name, defaultValue);
$form->set_element('text', 'tools', 'defaultValue');
This results into :
<input type="text" name="tools" value="defaultValue" />
In my class I set the value: if the form is posted, use that value, if not, use the default:
private function set_value( $name, $value='' ) {
if( $_SERVER['REQUEST_METHOD'] == 'POST' )
return $_POST[$name];
else
return $value;
}
When I want to add multiple "tools", I would like to use:
$form->set_element('text', 'tools[0]', 'defaultValue');
$form->set_element('text', 'tools[1]', 'defaultValue');
$form->set_element('text', 'tools[2]', 'defaultValue');
But in the set_value function
that gives $_POST['tools[0]'] instead of $_POST['tools'][0]

Use any number of variables in [] to access what you need:
$test = 'test';
$index = 0;
var_dump($_POST[$test][$index]);
$test = 'test';
$index = 0;
$subkey = 'key'
var_dump($_POST[$test][$index][$subkey]);
And so on.
There's no special function to achieve what you want, so you should write something, for example:
$key = 'test[0]';
$base = strstr($key, '[', true); // returns `test`
$ob_pos = strpos($key, '[');
$cb_pos = strpos($key, ']');
$index = substr($key, $ob_pos + 1, $cb_pos - $ob_pos - 1);
var_dump($arr[$base][$index]);
Edit by LinkinTED
$key = 'test[0]';
$base = $n = substr($name, 0, strpos($key, '[') );
preg_match_all('/\[([^\]]*)\]/', $key, $parts);
var_dump($arr[$base][$parts[1][0]]);

See how when you did $_POST['test'][0]; you just added [0] to the end? As a separate reference.
You have to do that.
$_POST[$test][0];
If you need both parts in variables then you need to use multiple variables, or an array.
$var = Array( "test", "0" );
$_POST[$test[0]][$test[1]];

Each dimension of an array is called by specifying the key or index together with the array variable.
You can reference a 3 dimensional array's element by mentioning the 3 indexes of the array.
$value = $array['index']['index']['index'];
Like,
$billno = $array['customers']['history']['billno'];
You can also use variables which has the index values that can be used while specifying the array index.
$var1 = 'customers';
$var2 = 'history';
$var3 = 'billno';
$billno = $array[$var1][$var2][$var3];

Related

PHP create an array with values that equal true

I have passed a series of parameters from a jQuery file to a PHP script for processing.
Some of the parameters include names, email, department, etc. The majority of the parameters will either be TRUE or FALSE.
I want to build an array to include all of the parameters that equal TRUE.
<?php
$value = $_POST['criteria'];
$firstname = $value['firstname'];
$email = $value['email'];
$department = $value['department'];
$parameter1 = $value['parameter1']; // equals TRUE
$parameter2 = $value['parameter2']; // equals FALSE
$parameter3 = $value['parameter3']; // equals TRUE
$parameter4 = $value['parameter4']; // equals TRUE
?>
So the results of the array I want to produce should look like this:
$array = ['parameter1', 'parameter3', 'parameter4'];
I know I must use a loop, but I am not exactly sure how to start it.
Edit
Here is where I create the variable criteria in jQuery, starting with a button click event:
$('#requestAppSubmit').on('click', function()
{
var criteria =
{
firstname: $('#firstname').val(),
email: $('#email').val(),
department: $('#department').val(),
// the next parameters check if a checkbox was checked
parameter1: $('#dashboard').is(':checked'),
parameter2: $('#schedules').is(':checked'),
parameter3: $('#finance').is(':checked'),
parameter4: $('#businessplan').is(':checked'),
// quite a few more parameters
}
// then I use a ajax post
$.post('process/editRep.php', {criteria:criteria}, function(data)
{
console.log(data);
//
});
});
At this point, using your suggestions below, the most I can output is this:
Array()
You can use array_filter() to keep only boolean values, and then, use array_keys() to get the names:
$value = [
'firstname'=>'foo',
'email'=>'bar',
'department'=>'baz',
'parameter1'=>true,
'parameter2'=>false,
'parameter3'=>true,
'parameter4'=>true
];
$array = array_filter($value, function($item) {
return $item === true;
});
$array = array_keys($array);
print_r($array);
Output:
Array
(
[0] => parameter1
[1] => parameter3
[2] => parameter4
)
If values are not booleans, you could also use :
$array = array_filter($value, function($item) {
return is_numeric($item) && $item == true;
});
This will work with '0' and '1'.
You don't need a loop at all, just two functions: array_filter to filter out the false values, and array_keys to get the keys:
$array = array_keys(array_filter($values));
// results = ['parameter1', 'parameter3', 'parameter4']
Using foreach:
foreach($value as $index => $bool){
if($bool){
$new_array[] = $index;
}
}
Will only work if your values are of bool type and not string
If they are strings just compare them using ==
I can guess from your question that you need to process a list of parameters you care what their contents are like name, department and email, as well as a boolean list of attributes, in the same POST request.
I would encapsulate all the boolean attributes you need to pass in an array:
<input type="checkbox" name="options[parameter1]"/>
<input type="checkbox" name="options[parameter2]"/>
...
and process it in PHP:
<?php
$options = $_POST['options'] ?? [];
$onlyTrueOptions = array();
foreach($options as $optionName => $value) {
if($value) // or another desidered comparison
$onlyTrueOptions[] = $optionName;
}
Never, really never use "static-incremented" variables. That's what you use arrays for.
$arr = array();
for($i = 1; $i<=4; $i++)
{
if(strcmp($value['parameter'.$i],"TRUE") === 0)
{
array_push($arr,"parameter$i");
}
}

Count vars in get_defined_vars

I have unknown number of variables, for example:
$number_one = array(21,5,4,33,2,45);
$number_two = array(1,5,14,23,42,35);
$number_three = array(13,33,45,17,2,7);
$number_four = array(2,44,5,21,23,33);
I count all defined vars with $arr = get_defined_vars();
How can I count number of vars - in his case number of all arrays?
I used foreach, but maybe I don't do this properly.
$i = 0;
foreach ($arr as $value) {
$i++;
echo '<br>';
foreach ($value as $val) {
echo $val.',';
}
}
echo $i;
I don't know why result is 8 :/
Try this:
<?php
$number_one = array(21,5,4,33,2,45);
$number_two = array(1,5,14,23,42,35);
$number_three = array(13,33,45,17,2,7);
$number_four = array(2,44,5,21,23,33);
$variable_s = 'adsfadfdfa';
$variable_n = 22;
$vararr = get_defined_vars();
// We want to exclude all the superglobals
$globalarrays = array(
'GLOBALS',
'_SERVER',
'_POST',
'_GET',
'_REQUEST',
'_SESSION',
'_COOKIE',
'_ENV',
'_FILES'
);
$narrays = 0;
foreach($vararr as $key => $variable) {
if ( !in_array($key, $globalarrays) && is_array($variable) ) {
echo $key . ' is an array<br />';
$narrays++;
}
}
echo '# arrays = ' . $narrays;
Notes:
The code counts only arrays, no scalars (is_array()).
It excludes the super global arrays like GLOBALS, _POST, etc.
Result:
number_one is an array
number_two is an array
number_three is an array
number_four is an array
# arrays = 4
it is all because, get_defined_vars() returns certain predefined indexes like GLOBALS, _POST, _GET, _COOKIE, _FILES and other indexes which are user defined, here in your case, those are number_one, number_two, number_three and number_four
for more details on get_defined_vars() you can refer the link
As the user defined indexes, are only after predefined indexes, you can use array_slice to slice your defined array.
$number_one = array(21,5,4,33,2,45);
$number_two = array(1,5,14,23,42,35);
$number_three = array(13,33,45,17,2,7);
$number_four = array(2,44,5,21,23,33);
$arr = get_defined_vars();
$arr = array_slice($arr, 5, count($arr));
echo count($arr);
This prints the 4.
The function get_defined_vars() gets all of the variables that are defined currently in the server including environment and server variables.
$number_one = array(21,5,4,33,2,45);
$number_two = array(1,5,14,23,42,35);
$number_three = array(13,33,45,17,2,7);
$number_four = array(2,44,5,21,23,33);
$arr = get_defined_vars();
print_r($arr);
Try this code and see the output in your browser. I'm sure you'll get to know how many variables are actually defined(including those defined by you)
For Reference: http://php.net/manual/en/function.get-defined-vars.php

PHP: Access nested property from variable [duplicate]

Is it possible to create a variable variable pointing to an array or to nested objects? The php docs specifically say you cannot point to SuperGlobals but its unclear (to me at least) if this applies to arrays in general.
Here is my try at the array var var.
// Array Example
$arrayTest = array('value0', 'value1');
${arrayVarTest} = 'arrayTest[1]';
// This returns the correct 'value1'
echo $arrayTest[1];
// This returns null
echo ${$arrayVarTest};
Here is some simple code to show what I mean by object var var.
${OBJVarVar} = 'classObj->obj';
// This should return the values of $classObj->obj but it will return null
var_dump(${$OBJVarVar});
Am I missing something obvious here?
Array element approach:
Extract array name from the string and store it in $arrayName.
Extract array index from the string and store it in $arrayIndex.
Parse them correctly instead of as a whole.
The code:
$arrayTest = array('value0', 'value1');
$variableArrayElement = 'arrayTest[1]';
$arrayName = substr($variableArrayElement,0,strpos($variableArrayElement,'['));
$arrayIndex = preg_replace('/[^\d\s]/', '',$variableArrayElement);
// This returns the correct 'value1'
echo ${$arrayName}[$arrayIndex];
Object properties approach:
Explode the string containing the class and property you want to access by its delimiter (->).
Assign those two variables to $class and $property.
Parse them separately instead of as a whole on var_dump()
The code:
$variableObjectProperty = "classObj->obj";
list($class,$property) = explode("->",$variableObjectProperty);
// This now return the values of $classObj->obj
var_dump(${$class}->{$property});
It works!
Use = & to assign by reference:
$arrayTest = array('value0', 'value1');
$arrayVarTest = &$arrayTest[1];
$arrayTest[1] = 'newvalue1'; // to test if it's really passed by reference
print $arrayVarTest;
In echo $arrayTest[1]; the vars name is $arrayTest with an array index of 1, and not $arrayTest[1]. The brackets are PHP "keywords". Same with the method notation and the -> operator. So you'll need to split up.
// bla[1]
$arr = 'bla';
$idx = 1;
echo $arr[$idx];
// foo->bar
$obj = 'foo';
$method = 'bar';
echo $obj->$method;
What you want to do sounds more like evaluating PHP code (eval()). But remember: eval is evil. ;-)
Nope you can't do that. You can only do that with variable, object and function names.
Example:
$objvar = 'classObj';
var_dump(${$OBJVarVar}->var);
Alternatives can be via eval() or by doing pre-processing.
$arrayTest = array('value0', 'value1');
$arrayVarTest = 'arrayTest[1]';
echo eval('return $'.$arrayVarTest.';');
eval('echo $'.$arrayVarTest.';');
That is if you're very sure of what's going to be the input.
By pre-processing:
function varvar($str){
if(strpos($str,'->') !== false){
$parts = explode('->',$str);
global ${$parts[0]};
return $parts[0]->$parts[1];
}elseif(strpos($str,'[') !== false && strpos($str,']') !== false){
$parts = explode('[',$str);
global ${$parts[0]};
$parts[1] = substr($parts[1],0,strlen($parts[1])-1);
return ${$parts[0]}[$parts[1]];
}else{
return false;
}
}
$arrayTest = array('value0', 'value1');
$test = 'arrayTest[1]';
echo varvar($test);
there is a dynamic approach for to many nested levels:
$attrs = ['level1', 'levelt', 'level3',...];
$finalAttr = $myObject;
foreach ($attrs as $attr) {
$finalAttr = $finalAttr->$attr;
}
return $finalAttr;

Assigning values to a large number of variables in php after an if ()

Do you know a better way to do thing when it comes to assigning values to a large number of variables after an if?
In my case it like this:
$akeType = array_key_exists('type',$handle);
$akeParent = array_key_exists('parent',$handle);
$akeUserName = array_key_exists('userName',$handle);
$akeUserId = array_key_exists('userId',$handle);
$akeCountryCode = array_key_exists('userId',$handle);
if ( $akeType && $akeParent && $akeUserName && $akeUserId & $akeCountryCode ) {
$listType = $handle['type'];
$listParent = $handle['parent'];
$listUserName = $handle['userName'];
$listUserId = $handle['userId'];
$foo = $_POST['foo'];
$bar = $_POST['bar'];
$listCountryCode = $handle['countryCode']; // Is there a way to clean up this part? The assignments to variables.
take a look at the extract -- Import variables into the current symbol table from an array
extract($handle, EXTR_OVERWRITE, "ake_");
You can do this with the somewhat more obscure code following:
$keys= array('type','parent','userName', 'userId');
foreach($keys as $key) {
$nametoset= "list".ucfirst($key);
$$nametoset= $handle[$key];
}
$$nametoset refers to the variable named like the string $nametoset.
Similar code may be used for the $ake... variables.
You can use Variable variables to set your variable list.
For your specific case, you can use the following code:
foreach ($handle as $key => $value) {
$var_name = 'list'.$key;
$$var_name = $value;
}
foreach ($_POST as $pkey => $pvalue) {
$$pkey = $pvalue;
}
These loops create variables depending on your arrays keys.

How to pass an array into a function, and return the results with an array

So I'm trying to learn how to pass arrays through a function, so that I can get around PHP's inability to return multiple values. Haven't been able to get anything to work so far, but here is my best try. Can anybody point out where I'm going wrong?
function foo($array)
{
$array[3]=$array[0]+$array[1]+$array[2];
return $array;
}
$waffles[0]=1;
$waffles[1]=2;
$waffles[2]=3;
foo($waffles);
echo $waffles[3];
For clarification: I want to be able to pass multiple variables into a function, do something, then return multiple variables back out while keeping them seperate. This was just an example I was trying to get working as a work around for not being able to return multiple variables from an array
You seem to be looking for pass-by-reference, to do that make your function look this way (note the ampersand):
function foo(&$array)
{
$array[3]=$array[0]+$array[1]+$array[2];
}
Alternately, you can assign the return value of the function to a variable:
function foo($array)
{
$array[3]=$array[0]+$array[1]+$array[2];
return $array;
}
$waffles = foo($waffles)
You're passing the array into the function by copy. Only objects are passed by reference in PHP, and an array is not an object. Here's what you do (note the &)
function foo(&$arr) { # note the &
$arr[3] = $arr[0]+$arr[1]+$arr[2];
}
$waffles = array(1,2,3);
foo($waffles);
echo $waffles[3]; # prints 6
That aside, I'm not sure why you would do that particular operation like that. Why not just return the sum instead of assigning it to a new array element?
function foo(Array $array)
{
return $array;
}
Try
$waffles = foo($waffles);
Or pass the array by reference, like suggested in the other answers.
In addition, you can add new elements to an array without writing the index, e.g.
$waffles = array(1,2,3); // filling on initialization
or
$waffles = array();
$waffles[] = 1;
$waffles[] = 2;
$waffles[] = 3;
On a sidenote, if you want to sum all values in an array, use array_sum()
I always return multiple values by using a combination of list() and array()s:
function DecideStuffToReturn() {
$IsValid = true;
$AnswerToLife = 42;
// Build the return array.
return array($IsValid, $AnswerToLife);
}
// Part out the return array in to multiple variables.
list($IsValid, $AnswerToLife) = DecideStuffToReturn();
You can name them whatever you like. I chose to keep the function variables and the return variables the same for consistency but you can call them whatever you like.
See list() for more information.
i know a Class is a bit the overkill
class Foo
{
private $sum = NULL;
public function __construct($array)
{
$this->sum[] = $array;
return $this;
}
public function getSum()
{
$sum = $this->sum;
for($i=0;$i<count($sum);$i++)
{
// get the last array index
$res[$i] = $sum[$i] + $sum[count($sum)-$i];
}
return $res;
}
}
$fo = new Foo($myarray)->getSum();
Here is how I do it. This way I can actually get a function to simulate returning multiple values;
function foo($array)
{
foreach($array as $_key => $_value)
{
$str .= "{$_key}=".$_value.'&';
}
return $str = substr($str, 0, -1);
}
/* Set the variables to pass to function, in an Array */
$waffles['variable1'] = "value1";
$waffles['variable2'] = "value2";
$waffles['variable3'] = "value3";
/* Call Function */
parse_str( foo( $waffles ));
/* Function returns multiple variable/value pairs */
echo $variable1 ."<br>";
echo $variable2 ."<br>";
echo $variable3 ."<br>";
Especially usefull if you want, for example all fields in a database
to be returned as variables, named the same as the database table fields.
See 'db_fields( )' function below.
For example, if you have a query
select login, password, email from members_table where id = $id
Function returns multiple variables:
$login, $password and $email
Here is the function:
function db_fields($field, $filter, $filter_by, $table = 'members_table') {
/*
This function will return as variable names, all fields that you request,
and the field values assigned to the variables as variable values.
$filter_by = TABLE FIELD TO FILTER RESULTS BY
$filter = VALUE TO FILTER BY
$table = TABLE TO RUN QUERY AGAINST
Returns single string value or ARRAY, based on whether user requests single
field or multiple fields.
We return all fields as variable names. If multiple rows
are returned, check is_array($return_field); If > 0, it contains multiple rows.
In that case, simply run parse_str($return_value) for each Array Item.
*/
$field = ($field == "*") ? "*,*" : $field;
$fields = explode(",",$field);
$assoc_array = ( count($fields) > 0 ) ? 1 : 0;
if (!$assoc_array) {
$result = mysql_fetch_assoc(mysql_query("select $field from $table where $filter_by = '$filter'"));
return ${$field} = $result[$field];
}
else
{
$query = mysql_query("select $field from $table where $filter_by = '$filter'");
while ($row = mysql_fetch_assoc($query)) {
foreach($row as $_key => $_value) {
$str .= "{$_key}=".$_value.'&';
}
return $str = substr($str, 0, -1);
}
}
}
Below is a sample call to function. So, If we need to get User Data for say $user_id = 12345, from the members table with fields ID, LOGIN, PASSWORD, EMAIL:
$filter = $user_id;
$filter_by = "ID";
$table_name = "members_table"
parse_str(db_fields('LOGIN, PASSWORD, EMAIL', $filter, $filter_by, $table_name));
/* This will return the following variables: */
echo $LOGIN ."<br>";
echo $PASSWORD ."<br>";
echo $EMAIL ."<br>";
We could also call like this:
parse_str(db_fields('*', $filter, $filter_by, $table_name));
The above call would return all fields as variable names.
You are not able to return 'multiple values' in PHP. You can return a single value, which might be an array.
function foo($test1, $test2, $test3)
{
return array($test1, $test2, $test3);
}
$test1 = "1";
$test2 = "2";
$test3 = "3";
$arr = foo($test1, $test2, $test3);
$test1 = $arr[0];
$test2 = $arr[1];
$test3 = $arr[2];
Another way is:
$NAME = "John";
$EMAIL = "John#gmail.com";
$USERNAME = "John123";
$PASSWORD = "1234";
$array = Array ("$NAME","$EMAIL","$USERNAME","$PASSWORD");
function getAndReturn (Array $array){
return $array;
}
print_r(getAndReturn($array));

Categories