PHP array parsing - php

I am wondering if there are any classes for parsing PHP arrays in the general sense that you are looking back and forth over elements matching search patterns.
For example, lets say that If element "xyz" was found then I want to search backwards through the array until element "abc" or "cba" is found (or X number of steps backward is reached).
So I'm not sure how to describe this other than "regex for arrays". Does anyone know of any classes for this? My goal is to find data patterns in arrays that contain elements indexed in a certain order.

The standard array functions in PHP should get you pretty close: (assuming your array is $arr)
$key = array_search("xyz", $arr, true);
if($key != false){
$subset = array_slice($arr, 0, $key);
$search2 = array_search("abc", $subset, true);
}
If you want to search backwards (formally, backwards) you can do so by reversing the array before searching it with array_reverse, and if you want to set a limit on steps backwards you can make a smaller slice.
array_search
array_slice

Related

Does array_values in PHP loop through all the items?

I want to know if inbuilt PHP array functions such as array_diff, array_keys or array_values (in comparison to array_walk) iterate through each item or do they have an internal algorithm through which they do the computation in one go?
This is important when I want to learn how to optimise PHP scripts which handle 100,000 items.
For e.g. this method:
public function narrowDown($BigArray, $Column, $regex)
{
# narrowDown to focus on columns with similar data
$Column = array_column($BigArray, $Column);
$Search = preg_quote($regex, '~');
$Matched = preg_grep('~'.$Search.'~', array_combine(array_keys($BigArray), $Column));
# recreate rows by intersecting with specified keys
return array_intersect_key($BigArray, $Matched);
}
This method finds out similar rows in a specified column by regex in a multi-dimensional array.
The array has 18 columns and 100,000 items. I was thinking what should be the best way to optimise such methods.
Feel free to also advise if I should shift to a different programming language.
Yes, they iterate through all items, also calls and their results are not cached in any way.
So if you will call array function twice with exactly same input, all the work will be done twice.

PHP: What is the searching algorithm implemented in array_search()?

I have an array of items on which I would like to apply search function. I am considering sorting the array and simply applying binary search for now as it need not be too complex, however if I run into problems I'll try other methods.
My question is; what is the search algorithm used in the array_search()? If it is indeed binary search I can use that.
PHP performs a linear search - here's the source
It has to be sequential search, because the array might not be sorted.
If you need to search an array often, use array_flip to convert it to an associative array where the values become the keys. Looking up keys in an array is a hash lookup.
It isn't a binary search.... it simply loops through the array until it finds the first matching element.... the internal equivalent of
foreach($haystack as $key => $value) {
if ($value == $needle) {
return $key;
}
}
Though for a fast search alternative, a Trie might be better than a binary search

Get arbitrary number of random elements from a php array in one line

I wanted to pull an arbitrary number of random elements from an array in php. I see that the array_rand() function pulls an arbitrary number of random keys from an array. All the examples I found online showed then using a key reference to get the actual values from the array, e.g.
$random_elements = array();
$random_keys = array_rand($source_array);
foreach ( $random_keys as $random_key ) {
$random_elements[] = $source_array[$random_key];
}
That seemed cumbersome to me; I was thinking I could do it more concisely. I would need either a function that plain-out returned random elements, instead of keys, or one that could convert keys to elements, so I could do something like this:
$random_elements = keys_to_elements(array_rand($source_array, $number, $source_array));
But I didn't find any such function(s) in the manual nor in googling. Am I overlooking the obvious?
What about usung array_flip? Just came to my mind:
$random_elements = array_rand(array_flip($source_array), 3);
First we flip the array making its values become keys, and then use array_rand.
An alternate solution would be to shuffle the array and return a slice from the start of it.
Or, if you don't want to alter the array, you could do:
array_intersect_key($source_array, array_combine(
array_rand($source_array, $number), range(1, $number)));
This is a bit hacky because array_intersect can work on keys or values, but not selecting keys from one array that match values in another. So, I need to use array_combine to turn those values into keys of another array.
You could do something like this, not tested!!!
array_walk(array_rand($array, 2), create_function('&$value,$key',
'$value = '.$array[$value].';'));

PHP: Find common repeating string?

I have this situation in PHP. I have an array that has these keys for example, wires-1, wires-2, wires-3. I need a function or way for my program to read these keys, and find that the common word is wires? How would that be accomplished in PHP? Thanks for your help.
Take a look at how an autocomplete's functionality works, this is similar to your approach.
I'm sure there's plenty of source codes for autocomplete on google
For the string value of every key in your array:
Throw away all non-alpha characters, i.e. leave only letters such that ctype_alpha($remaining_text) should return true.
Keep an array with the found words as keys, and their frequencies as values, as such:
$array = new array();
function found_word($word)
{ global $array;
if(!isset($array[$word])) { $array[$word] = 1; }
else { $array[$word]++; }
}
Only nicer ;)
Sort the array in reverse by using arsort($array);
$array now contains the most found words as its first elements.
you would have to create every possible suffix of every string you have.
create a map for every suffix you found
count the occurence of every suffix in your string array
you can modify the performance with f.ex. limiting the suffix length

Alternative to array_shift function

Ok, I need keys to be preserved within this array and I just want to shift the 1st element from this array. Actually I know that the first key of this array will always be 1 when I do this:
// Sort it by 1st group and 1st layout.
ksort($disabled_sections);
foreach($disabled_sections as &$grouplayout)
ksort($grouplayout);
Basically I'd rather not have to ksort it in order to grab this array where the key = 1. And, honestly, I'm not a big fan of array_shift, it just takes to long IMO. Is there another way. Perhaps a way to extract the entire array where $disabled_sections[1] is found without having to do a foreach and sorting it, and array_shift. I just wanna add $disabled[1] to a different array and remove it from this array altogether. While keeping both arrays keys structured the way they are. Technically, it would even be fine to do this:
$array = array();
$array = $disabled_sections[1];
But it needs to remove it from $disabled_sections. Can I use something like this approach...
$array = array();
$array = $disabled_sections[1];
$disabled_sections -= $disabled_sections[1];
Is something like the above even possible??
Thanks.
Despite there being an accepted answer to this; in case someone else stumbles across this, a way to unset the first element of an array (regardless of its key, or the order of its keys) without using array_shift is:
reset($array); // sets internal array pointer to start
unset($array[key($array)]); // key() returns key of current array element
Though I'm fairly convinced that's what array_shift does internally (so I imagine there would be no performance gain to this), excepting an additional return of the value retrieved:
$element = reset($array); // also returns element
unset($array[key($array)]);
return $element;
Just for completion's sake.
While there's no -= operator in that fashion, you can use unset to remove that element from an array:
unset(disabled_sections[1]);
But that's just implementing your own version of shift. I do wonder under what situation you're finding array_shift() to be 'slow' and how you're testing said slowness.
Numeric arrays are sorted numerical by default - no ksort is required. Maybe you should try something like
while($array = array_shift($group_of_arrays)) {
// ... do stuff
}
If you are not concerned about the order in which you pull elements out of the array, you can use "array_pop" instead of "array_shift". Since "array_pop" takes the elements off of the end of the array, no reindexing is required and performance increases dramatically. In testing with an array of about 80,000 entries I am seeing about a 90% decrease in processing time with "array_pop".

Categories