I have a need to check if the elements in an array are objects or something else. So far I did it like this:
if((is_object($myArray[0]))) { ... }
However, on occasion situations dictate that the input array does not have indexes that start with zero (or aren't even numeric), therefore asking for $myArray[0] will generate a Notice, but will also return the wrong result in my condition if the first array element actually is an object (but under another index).
The only way I can think of doing here is a foreach loop where I would break out of it right on the first go.
foreach($myArray as $element) {
$areObjects = (is_object($element));
break;
}
if(($areObjects)) { ... }
But I am wondering if there is a faster code than this, because a foreach loop seems unnecessary here.
you can use reset() function to get first index data from array
if(is_object(reset($myArray))){
//do here
}
You could get an array of keys and get the first one:
$keys = array_keys($myArray);
if((is_object($myArray[$keys[0]]))) { ... }
try this
reset($myArray);
$firstElement = current($myArray);
current gets the element in the current index, therefore you should reset the pointer of the array to the first element using reset
http://php.net/manual/en/function.current.php
http://php.net/manual/en/function.reset.php
Related
This question has been asked a thousand times, but each question I find talks about associative arrays where one can delete (unset) an item by using they key as an identifier. But how do you do this if you have a simple array, and no key-value pairs?
Input code
$bananas = array('big_banana', 'small_banana', 'ripe_banana', 'yellow_banana', 'green_banana', 'brown_banana', 'peeled_banana');
foreach ($bananas as $banana) {
// do stuff
// remove current item
}
In Perl I would work with for and indices instead, but I am not sure that's the (safest?) way to go - even though from what I hear PHP is less strict in these things.
Note that after foreach has run, I expected var_dump($bananas) to return an empty array (or null, but preferably an empty array).
1st method (delete by value comparison):
$bananas = array('big_banana', 'small_banana', 'ripe_banana', 'yellow_banana', 'green_banana', 'brown_banana', 'peeled_banana');
foreach ($bananas as $key=>$banana) {
if($banana=='big_banana')
unset($bananas[$key]);
}
2nd method (delete by key):
$bananas = array('big_banana', 'small_banana', 'ripe_banana', 'yellow_banana', 'green_banana', 'brown_banana', 'peeled_banana');
unset($bananas[0]); //removes the first value
unset($bananas[count($bananas)-1]); //removes the last value
//unset($bananas[n-1]); removes the nth value
Finally if you want to reset the keys after deletion process:
$bananas = array_map('array_values', $bananas);
If you want to empty the array completely:
unset($bananas);
$bananas= array();
it still has the indexes
foreach ($bananas as $key => $banana) {
// do stuff
unset($bananas[$key]);
}
for($i=0; $i<count($bananas); $i++)
{
//doStuff
unset($bananas[$i]);
}
This will delete every element after its use so you will eventually end up with an empty array.
If for some reason you need to reindex after deleting you can use array_values
How about a while loop with array_shift?
while (($item = array_shift($bananas)) !== null)
{
//
}
Your Note: Note that after foreach has run, I expected var_dump($bananas) to return an empty array (or null, but preferably
an empty array).
Simply use unset.
foreach ($bananas as $banana) {
// do stuff
// remove current item
unset($bananas[$key]);
}
print_r($bananas);
Result
Array
(
)
This question is old but I will post my idea using array_slice for new visitors.
while(!empty($bananas)) {
// ... do something with $bananas[0] like
echo $bananas[0].'<br>';
$bananas = array_slice($bananas, 1);
}
How to check if a string is already in array, but during checking exclude last element of that array? By now, I'm using a workaround with unset() and re-declaration like this:
$fkTableName = $fkTableArr[$colNr0];
unset($fkTableArr[$colNr0]);
if (!in_array($fkTableName, $fkTableArr))
// do sth
$fkTableArr[$colNr0] = $fkTableName;
but it seems pretty redundant to me.
Use array_slice() to slice the array and use it. The below code doesn't include the last element in the array.
array_slice($input, -1);
So your code becomes:
$fkTableName = $fkTableArr[$colNr0];
if (!in_array($fkTableName, array_slice($fkTableArr, -1)))
// do sth
If you want to not affect the array, try this:
if (in_array($fkTableName, $fkTableArr) && $fkTableName != end($fkTableArr)) {
// element in array, but not last item
}
In the PHP manual, (array_push) says..
If you use array_push() to add one element to the array it's better to
use $array[] = because in that way there is no overhead of calling a
function.
For example :
$arr = array();
array_push($arr, "stackoverflow");
print_r($arr);
vs
$arr[] = "stackoverflow";
print_r($arr);
I don't understand why there is a big difference.
When you call a function in PHP (such as array_push()), there are overheads to the call, as PHP has to look up the function reference, find its position in memory and execute whatever code it defines.
Using $arr[] = 'some value'; does not require a function call, and implements the addition straight into the data structure. Thus, when adding a lot of data it is a lot quicker and resource-efficient to use $arr[].
You can add more than 1 element in one shot to array using array_push,
e.g. array_push($array_name, $element1, $element2,...)
Where $element1, $element2,... are elements to be added to array.
But if you want to add only one element at one time, then other method (i.e. using $array_name[]) should be preferred.
The difference is in the line below to "because in that way there is no overhead of calling a function."
array_push() will raise a warning if the first argument is not
an array. This differs from the $var[] behaviour where a new array is
created.
You should always use $array[] if possible because as the box states there is no overhead for the function call. Thus it is a bit faster than the function call.
array_push — Push one or more elements onto the end of array
Take note of the words "one or more elements onto the end"
to do that using $arr[] you would have to get the max size of the array
explain:
1.the first one declare the variable in array.
2.the second array_push method is used to push the string in the array variable.
3.finally it will print the result.
4.the second method is directly store the string in the array.
5.the data is printed in the array values in using print_r method.
this two are same
both are the same, but array_push makes a loop in it's parameter which is an array and perform $array[]=$element
Thought I'd add to the discussion since I believe there exists a crucial difference between the two when working with indexed arrays that people should be aware of.
Say you are dynamically creating a multi-dimensional associative array by looping through some data sets.
$foo = []
foreach ($fooData as $fooKey => $fooValue) {
foreach ($fooValue ?? [] as $barKey => $barValue) {
// Approach 1: results in Error 500
array_push($foo[$fooKey], $barKey); // Error 500: Argument #1 ($array) must be of type array
// NOTE: ($foo[$fooKey] ?? []) argument won't work since only variables can be passed by reference
// Approach 2: fix problem by instantiating array beforehand if it didn't exist
$foo[$fooKey] ??= [];
array_push($foo[$fooKey], $barKey);
// Approach 3: One liner approach
$foo[$fooKey][] = $barKey; // Instantiates array if it doesn't exist
}
}
Without having $foo[$fooKey] instantiated as an array beforehand, we won't be able to do array_push without getting the Error 500. The shorthand $foo[$fooKey][] does the heavy work for us, checking if the provided element is an array, and if it isn't, it creates it and pushes the item in for us.
I know this is an old answer but it might be helpful for others to know that another difference between the two is that if you have to add more than 2/3 values per loop to an array it's faster to use:
for($i = 0; $i < 10; $i++){
array_push($arr, $i, $i*2, $i*3, $i*4, ...)
}
instead of:
for($i = 0; $i < 10; $i++){
$arr[] = $i;
$arr[] = $i*2;
$arr[] = $i*3;
$arr[] = $i*4;
...
}
edit- Forgot to close the bracket for the for conditional
No one said, but array_push only pushes a element to the END OF THE ARRAY, where $array[index] can insert a value at any given index. Big difference.
Stumped by this one:
I have a function that returns an array of folders in a given directory. When I iterate through the array, I can see all the items. However, if I try to print the first item, I get nothing:
function get_folders($dir) {
return array_filter(scandir($dir), function ($item) use ($dir) {
return (is_dir($dir.'/'.$item) && $item != "." && $item != "..") ;
});
}
$folders = get_folders(".");
$first_folder = $folders[0];
echo $first_folder; // returns blank.
Interestingly, if I don't filter out the "." and "..", then $first_folder does print ".". Can anyone explain this?
As noted in the manual: Array keys are preserved when using array_filter().
The keys are preserved from the call to scandir() which will include the . and .. directories, meaning your filtered array will start at 2 or more (whatever the key is for the first directory).
A simple fix would be to wrap the whole thing in array_values() to get the resultant array having keys starting from 0 and incrementing by one.
return array_values(array_filter(...));
If you don't actually care about the keys, then basic array functions could be of use like key or current.
From the array_filter manual:
Iterates over each value in the input array passing them to the callback function. If the callback function returns true, the current value from input is returned into the result array. Array keys are preserved.
So, scandir($dir) gets you an array with . at key 0, thus if you later filter . out, there will be nothing at key 0 in the result.
If you want to know what the first key of the resulting array is, try the array_keys function.
EDIT: actually, salathe's suggestion to use array_values is better in your case than getting the keys from array_keys.
can you print the folders and see if there is some key you can get the first folder with as opposed to selecting the index of zero? It seems lke $folders[0] would work unless the entries are stored with a different set of indexes / keys.
Try doing a
print_r($folders)
to see if it outputs your first folder and all other folders as expected with the corresponding indexes you're looking for.
array_filter preserves array keys, so if the first two elements have been removed, then the "new first" element has an index of 2. To convert that into an array indexed starting from 0, use array_values:
return array_values(array_filter(scandir($dir), function ($item) use ($dir) {
...
As others have said, array_filter preserves the keys in the array. Given that initially the item '.' has key 0, the filtered array ends up not having any item with key 0 (you can verify this with print_r($folders). So this line:
$first_folder = $folders[0];
ends up generating an E_NOTICE saying that there is no key 0 in the array (having notices turned on would alert you to the cause of the problem immediately, I highly recommend it) and giving $first_folder the value null.
To get the first value of the filtered array, regardless of key, use reset:
$first_folder = reset($folders);
if($first_folder === false) {
echo 'No folders!';
}
else {
echo 'First folder: '.$first_folder;
}
This might sounds like a silly question. How do I get the 1st value of an array without knowing in advance if the array is associative or not?
In order to get the 1st element of an array I thought to do this:
function Get1stArrayValue($arr) { return current($arr); }
is it ok?
Could it create issues if array internal pointer was moved before function call?
Is there a better/smarter/fatser way to do it?
Thanks!
A better idea may be to use reset which "rewinds array's internal pointer to the first element and returns the value of the first array element"
Example:
function Get1stArrayValue($arr) { return reset($arr); }
As #therefromhere pointed out in the comment below, this solution is not ideal as it changes the state of the internal pointer. However, I don't think it is much of an issue as other functions such as array_pop also reset it.
The main concern that it couldn't be used when iterating over an array isn't an problem as foreach operates on a copy of the array. The PHP manual states:
Unless the array is referenced, foreach operates on a copy of the specified array and not the array itself.
This can be shown using some simple test code:
$arr = array("a", "b", "c", "d");
foreach ( $arr as $val ){
echo reset($arr) . " - " . $val . "\n";
}
Result:
a - a
a - b
a - c
a - d
To get the first element for any array, you need to reset the pointer first.
http://ca3.php.net/reset
function Get1stArrayValue($arr) {
return reset($arr);
}
If you don't mind losing the first element from the array, you can also use
array_shift() - shifts the first value of the array off and returns it, shortening the array by one element and moving everything down. All numerical array keys will be modified to start counting from zero while literal keys won't be touched.
Or you could wrap the array into an ArrayIterator and use seek:
$array = array("foo" => "apple", "banana", "cherry", "damson", "elderberry");
$iterator = new ArrayIterator($array);
$iterator->seek(0);
echo $iterator->current(); // apple
If this is not an option either, use one of the other suggestions.