PHP Unsetting data in an array - php

I have the following line which reads a csv and turns each row into an Array
$reader = new CSV\CSVReader('somecsv.csv');
So if I then do
while ($row = $reader->getRow()) {
print "<pre>";
print_r($row);
print "</pre>";
}
It outputs data like so
Array
(
[Column1] => some
[Column2] => data
[Column3] => hi
[Column4] => wow
[Column5] => help
)
Array ...
Say I wanted to remove column1, inside the while loop I can place
unset($row['column1']);
And this will remove column1 from the output. However, if I place a function in my $reader class like so
public function unsetColumns($row)
{
unset($row['column1']);
}
And I change my while loop to the following
while ($row = $reader->getRow()) {
$reader->unsetColumns($row); //this does not work
unset($row['column1']); //this works
print "<pre>";
print_r($row);
print "</pre>";
}
Then the function call does not remove the column, but the unset does. I dont have both in there at the same time, just put them both there so you can see what works and what does not.
Why would this be?
Thanks

You can pass your array by reference read here more on Passing by Reference
public function unsetColumns(&$row)
{
unset($row['column1']);
}
while ($row = $reader->getRow()) {
$reader->unsetColumns($row); //this does not work
unset($row['column1']); //this works
print "<pre>";
print_r($row);
print "</pre>";
}

You are just passing $row, it is getting deleted in function call also.
But, you are not returning it (neither you are passing reference to $row).
Do two changes:
$row = $reader->unsetColumns($row);
And
public function unsetColumns($row)
{
unset($row['column1']);
return $row;
}
So, that your column deletion activity gets used.

You can pass the current $row by reference it to manipulate inside a function and also see those changes outside of that functions scope.
<?php
public function unsetColumns( &$row )
{
unset( $row['column1'] );
}
while( $row = $reader->getRow() ) {
$reader->unsetColumns( $row );
print "<pre>";
print_r($row);
print "</pre>";
}
The difference to your existing code is the additional ampersand in front of the arguments name: &$row in the function declaration.
See: http://php.net/manual/en/language.references.pass.php

Related

Why array is not updated when i want to print it out (print_r)?

<!DOCTYPE html>
<html>
<body>
<?php
$array_task=array();
fillArray($array_task);
function fillArray($array){
$array1=array();
$array2=array();
for ($i=0;$i<8;$i++){
$array1[$i]=$i+1;
$array2[$i]=rand(0,100);
}
$array=array_combine($array1,$array2);
echo"Array before any editions <br>";
print_r($array);
echo"<br>Array after adding sum and multiplication <br>";
addSumMulti($array);
print_r($array);
echo"<br>Array after adding last element after each array element <br>";
#addAfterEach($array);
}
function addSumMulti($array){
$sum=0;
$multiplication=1;
for ($i=1;$i<=10;$i++){
$sum+=$array[$i];
if ($i==3 || $i==4){
$multiplication*=$array[$i];
}
}
$array[9]=$sum;
$array[10]=$multiplication;
print_r($array);
echo "<br>";
}
?>
</body>
</html>
first print_r ($array) shows 8elements, then in the next function i add 2 elements. And print_r in the function addSumMulti shows 10 elements, but print_r after function addSumMulti inside the fillArray shows only 8 elements. What is wrong, what should I change so that i could see 10 elements in print_r after addSumMulti (21 line)?
In PHP ordinary variables are passed by value*. So, when you pass your array to your function a new copy is made which your function code manipulates. Your function doesn't return any values, so the new values of your array are lost, and the calling code sees only the original copy of the array.
There are two ways to make the changes to the original array:
return a value from the function. e.g.:
function addLine($arr) {
$arr[] = "Additional Line";
return $arr
}
$arr = ["First line"];
$arr = addLine($arr);
or pass in the variable by reference. E.g:
function addLine(&$arr) {
$arr[] = "Additional Line";
return $arr
}
$arr = ["First line"];
addLine($arr);
See Variable scope and Passing By Reference
*Objects are always passed by reference
Your $array has not been updated due to variable scope.
$array declared inside fillArray() cannot be referenced in another function. To do so It should be global variable.
Either modify the function addSumMulti to return an array and use the same in fillArray OR make $array as a global variable.
Option 1:
function fillArray($array){
.....
$arrayAfterSum = addSumMulti($array);
.....
}
function addSumMulti($array){
.....
.....
return $array;
}
Option 2:
$array = array(); // its a gloabal variable
function fillArray($array){
global $array; // in order to access global inside function
.....
.....
}
function addSumMulti($array){
global $array; // in order to access global inside function
.....
.....
}

how to add elements to an array inside a function php

how to add elements to a global array from inside a function if element not exist in array?
my main code will call to function multiple times.but each time different elements will create inside the function
my sample current code is,
$all=[];
t(); // 1st call
t(); //2nd call
function t(){
$d='2,3,3,4,4,4'; //this is a sample.but element will different for each function calling
$d=explode(',',$d);
foreach($d as $e){
if(!in_array($e,$all)){
array_push($all, $e);
}
}
}
print_r($all);
output is empty,
Array()
but i need it like this
Array
(
[0] => 2
[1] => 3
[2] => 4
)
thank you
If you look at the variable scope in PHP http://php.net/manual/en/language.variables.scope.php
You'll see that functions don't have access to the outer scope.
Therefore you'll need to do either pass the array by reference:
function t(&$myarray)
Create an array inside of the function and returning that one
function t(){
$all = [];
$d='2,3,3,4,4,4';
$d=explode(',',$d);
foreach($d as $e){
if(!in_array($e,$all)){
array_push($all, $e);
}
}
return $all;
}
Or if you want to keep adding to the array you can do
function t($all){
$d='2,3,3,4,4,4';
$d=explode(',',$d);
foreach($d as $e){
if(!in_array($e,$all)){
array_push($all, $e);
}
}
return $all;
}
Then calling the function with $all = t($all);
Your code will show errors as $all isn't in the scope of the function, you need to pass the value in to have any effect...
<?php
error_reporting(E_ALL);
ini_set('display_errors', 1);
$all=[];
t($all); // 1st call
t($all); //2nd call
function t( &$data){
$d='2,3,3,4,4,4'; //this is a sample.but element will different for each function calling
$d=explode(',',$d);
foreach($d as $e){
if(!in_array($e,$data)){
array_push($data, $e);
}
}
}
print_r($all);
Result
Array
(
[0] => 2
[1] => 3
[2] => 4
)
You can use global, but this is generally discouraged.
To add on Alexy's response regarding the use of 'array_unique($d)', which I recommend as it eliminates the need for the loop. You can pass the filtered array to array_values($d) to index your elements as shown by the results you want to achieve. FYI: array_unique will preserve the original keys: http://php.net/manual/en/function.array-unique.php
Your case will require removing duplicates a few times its best to have a separate function for that:
$all = [];
function t(){
global $all;//Tell PHP that we are referencing the global $all variable
$d='2,3,3,4,4,4';
$d=explode(',',$d);
$d=rmvDuplicates($d);
$all = array_merge($all,$d);//Combine the new array with what we already had
$all = rmvDuplicates($all);
}
function rmvDuplicates(array){
$array=array_unique($d);
$array=array_values($d);
return $array;
}

Joining string, variable, and array index all together to a variable

I'm trying to do something out of my league, but I don't see how else I can achieve it.
I have two array variables.
<?php
$mobile_eu = array("alb", "bul");
$m_alb = array(array("Albanian"), array("test#test.com"),
array("test2#test.com", "test3#test.com");
?>
What I'm trying to do is, get alb from $mobile_eu, prepend a string to the value, and then access $m_alb from it with [0][0] index. Something like...
function createLink($category) {
foreach ($category as $short) {
$langcode = "\$m_" . $short . [0][0];
}
}
and yes, it doesn't work. When I dumped it, all it shows is
string 'alb0' (length=4)
What I hope to achieve here is to get
string 'Albanian' (length=8)
Is there any way to get this?
Any help would be great.
Thanks.
<?php
$mobile_eu = array("alb", "bul");
$m_alb = array(array("Albanian"), array("test#test.com"),
array("test2#test.com", "test3#test.com"));
echo ${'m_'.$mobile_eu[0]}[0][0];
prints Albania.
see also: http://docs.php.net/language.variables.variable
But I think you should structure your data in another way, so you don't need something like this. E.g. instead of having a variable $m_alb and another $m_bul you could have an array where 'alb' and 'bul' are keys/elements:
<?php
createLinks( array('alb','bul') );
function createLinks($regions) {
static $data = array ( /* using static only as an example for "some data source" */
'alb' => array(
array("Albanian"), /* it would certainly be nice if you could give */
array("test#test.com"), /* those elements key-names with some meaning */
array("test2#test.com", "test3#test.com")
),
'bul' => array(
array("Bulgaria"),
array("test5#test.com"),
array("test6#test.com", "test7#test.com")
),
);
foreach( $regions as $r ) {
echo $data[$r][0][0], "<br />\r\n";
}
}
Might be this will helps you.
Solution : I have made some modifications in your createlink function Kindly check those as below:
function createLink($category) {
foreach ($category as $short) {
global $m_alb;
$arrayName = "m_" . $short;
$newArray = $$arrayName;
var_dump($newArray[0][0]);
}
}
I have made $m_alb array as the global because the with out this we will get an Notice: Undefined variable: m_alb. As the $m_alb array is not in the scope of createlink function. Now you can call your createlink function and check the result.
Hope this will works for you.

Call a function within a function display both within array

how do I call a function from within a function?
function tt($data,$s,$t){
$data=$data;
echo '[[';
print_r($data);
echo ']]';
if($t==0){
$data[]=$s;
tt($data,'two',1);
}else{
$data[]=$s;
}
return $data;
}
print_r(tt('','one',0));
I want 'two' to be shown within the array like
$o[]='one';
$o[]='two';
print_r($o);
function tt($s, $t, array $data = array()) {
$data[] = $s;
if ($t == 0) {
$data = tt('two', 1, $data);
}
return $data;
}
print_r(tt('one', 0));
This is all that's really needed.
Put the array as the last argument and make it optional, because you don't need it on the initial call.
When calling tt recursively, you need to "catch" its return data, otherwise the recursive call simply does nothing of lasting value.
No need for the else, since you're going to append the entry to the array no matter what and don't need to write that twice.
Try this one (notice the function signature, the array is passed by ref &$data):
function tt(&$data,$s,$t){
echo '[[';
print_r($data);
echo ']]';
if($t==0){
$data[]=$s;
tt($data,'two',1);
}else{
$data[]=$s;
}
return $data;
}
$array = [];
tt($array,'one',0);
print_r($array);
/**
Array
(
[0] => one
[1] => two
)
*/
try this
function tt($data,$s,$t){
global $data;
if($t==0){
$data[]=$s;
tt($data,'two',1);
}else{
$data[]=$s;
}
return $data;
}
print_r(tt('','one',0));
OUTPUT :
Array
(
[0] => one
[1] => two
)
DEMO

Recursive function with unknown depth of values. Return all values (undefined depth)

I have a question about a recursive PHP function.
I have an array of ID’s and a function, returning an array of „child id’s“ for the given id.
public function getChildId($id) {
…
//do some stuff in db
…
return childids;
}
One childid can have childids, too!
Now, I want to have an recursive function, collecting all the childids.
I have an array with ids like this:
$myIds = array("1111“,"2222“,"3333“,“4444“,…);
and a funktion:
function getAll($myIds) {
}
What I want: I want an array, containing all the id’s (including an unknown level of childids) on the same level of my array. As long as the getChildId($id)-function is returning ID’s…
I started with my function like this:
function getAll($myIds) {
$allIds = $myIds;
foreach($myIds as $mId) {
$childids = getChildId($mId);
foreach($childids as $sId) {
array_push($allIds, $sId);
//here is my problem.
//what do I have to do, to make this function rekursive to
//search for all the childids?
}
}
return $allIds;
}
I tried a lot of things, but nothing worked. Can you help me?
Assuming a flat array as in your example, you simply need to call a function that checks each array element to determine if its an array. If it is, the function calls it itself, if not the array element is appended to a result array. Here's an example:
$foo = array(1,2,3,
array(4,5,
array(6,7,
array(8,9,10)
)
),
11,12
);
$bar = array();
recurse($foo,$bar);
function recurse($a,&$bar){
foreach($a as $e){
if(is_array($e)){
recurse($e,$bar);
}else{
$bar[] = $e;
}
}
}
var_dump($bar);
DEMO
I think this code should do the trick
function getAll($myIds) {
$allIds = Array();
foreach($myIds as $mId) {
array_push($allIds, $mId);
$subids = getSubId($mId);
foreach($subids as $sId) {
$nestedIds = getAll($sId);
$allIds = array_merge($allIds, $nestedIds);
}
}
return $allIds;
}

Categories