Sorry for a silly quastion, more like a request..
Been using array_keys but suddenly swapped it with array_flip and saw no difference, can somebody benchmark it? ::
The two functions perform different tasks. Do you need keys exchanged with their associated values? Or do you just need all keys? Use whichever one you need to achieve the task.
There are pretty much always many routes to take that achieve the same outcome, but (eg) perhaps it doesn't matter if the array order is changed or not, then don't use the one which flips as it'll (theoretically/speculatively) take longer and it's not the right tool for the task.
If you have huge sets of data and/or many iterations of it, and as such these things are relevant to you, then you should have benchmark systems setup to test this scenario and likely others. If not then like most applications, such considerations are micro-optimisation and choice of the tool/function should be one which fits the task - and suits your code base or framework, coding style, etc.
Choosing the one which suits the task also makes intent more clear. So eg if you don't need to flip the array, even if that function is marginally faster, use the one you actually need otherwise a future refactor might leave someone scratching their head a little at your choice of using array_flip().
array_flip
array_flip — Exchanges all keys with their associated values in an
array
$input = array("oranges", "apples", "pears");
$flipped = array_flip($input);
Array
(
[oranges] => 0
[apples] => 1
[pears] => 2
)
array_keys
array_keys — Return all the keys or a subset of the keys of an array
$array = array(0 => 100, "color" => "red");
print_r(array_keys($array));
Array
(
[0] => 0
[1] => color
)
Do you need them flipped? Or do you just need the keys? If not need flipped then use the latter, else use the former.
Array flip also states
If a value has several occurrences, the latest key will be used as its value, and all others will be lost.
Maybe this is a problem to you? Maybe it doesn't matter?
Related
So I am a programmer who is pretty ok with the regular decision tree based algorithms and even with optimizations related to making small enhancements by skipping an extra step in calculation or even tweaking queries a bit to make our apps faster.
I am facing a problem that is a bit more algorithmically complex to solve than I am used to. The idea is that I will have this data array of say, a thousand elements. Each element of the data array is an array of its own with an additional 5-10 elements.
I will another value array for which I have to find the best matching ten array element nodes from the first and return in the best matching sequence.
Some sample data to visualize:
say the value array looks so:
$arr = array(
elm1 = 0.125,
elm2 = 5
elm3 = 200
);
and the data array will look something like:
$array = array(
[0] => array(elm1 => 1.5, elm2 => 8, elm3 => 10),
[1] => array(elm1 => 0.5, elm2 => 4, elm3 => 100),
...etc..
);
Now the idea is that for each element [elm1, elm2, elm3 etc] I will give a weightage based on how close the values are for that element in the value array and in each of the data array nodes then based on that I need to extract the ten best matching data array node elements.
This looks fine in theory, but I am worried about the processing time because users would wait for this in real time. Now I am not a big math guy, even though I have tried to understand the big(O), n(p) stuff, it flies over my head.
So I am looking at a more layman-programmer solution rather than going deep into how algorithm complexity works..I am thinking if I created different arrays where the indexes were say elm1, elm2 etc, and then perhaps sort each of those array and run a quick sort it might help. I was curious to know how anyone in this community would tackle an issue like this.
Any pointers are greatly appreciated!
DISCLAIMER: I am not a PHP guy.
In general, or from algorithmic perspective the best solution would be to keep the data you have in bi-dimensional array in a sorted map collection.
I was able to find this implementation of SortedMap in PHP. After you insert all your data there, searching for a matching element from you second array there would be a logarithmic or O(log n) .
Hope this helps...
If I have an array which is using numerical keys and I add a key far outside the range so far, does it create the intermediate keys as well. For example if I have
$array = array(1,2,3,4);
$array[9] = 10;
Will this cause php to internally reserve memory for the keys 4-8 even though they don't have a value with them.
The reason I ask is I have a large 2D array which I want to use for memoization in a dynamic programming algorithm because only a small number of the total cells will need to be computed. However it would be taxing on the memory to have an empty array of that size for the full 2D array. Is there a better way to do 2 key memoization? I could use an associative array and append the keys with a separator or some scheme like that but if php won't make the extra keys I would rather (for simplicity and readability) just use the 2D array. Thoughts?
This may not fully answer your question, but should help in finding an answer, at least to the first question.
Create this program.
$arr = array(1, 2, 3, 4);
sleep(10);
$arr[100000] = 1;
sleep(10);
Now run it and monitor its memory usage.
In the first ten seconds, the program reserves memory for a small array.
In the next ten seconds, if the array reserves space for the unused indices, the memory usage goes ridiculously high compared to the previous one. If it doesn't, though, the memory used will only grow slightly.
This should give you an idea of the effect of your final program, whether or not using a 2D array is a good idea.
Don't worry, it won't make any extra keys. PHP is not like that, even arrays that you think are regular are associative arrays. You can even combine PHP arrays like this:
array(
1 => 121,
2 => 2112,
'stuff' => array('morestuff'),
'foo' => 1231
)
With PHP its very comfortable which can be good and bad also.
It doesn't seem like it will allocate a placeholder or use any memory for the unused keys, based on Doug T.'s response. Hope this helps!
I typically code in Python, Java, or C. I'm taking on a project in PHP and I'm reading up on arrays in PHP and I'm utterly baffled. If I am understanding correctly, the numerical indices in PHP don't necessarily correspond to position and are just keys like in a dict in Python. So, when you shuffle a PHP array, the order of the elements will change, but their keys will remain the same. So when calling array[9], you might actually be getting the first element of the array if the shuffle ordered the elements that way. This raises a bunch of questions:
Is a PHP array, then, always just some kind of ordered hash table?
And what does that mean for overhead? In Python, lists function like
a classic array data structure and dictionaries more along the lines
of a hash structure. PHP seems to combine the two by assigning unique
keys to every value AND keeping track of the order of those values. If I want to use an associative array structure for constant time lookup, am I in a far worse off position than I would be with a Python dictionary because of this ordering overhead? Are there PHP data structures that are ONLY arrays or ONLY hash tables?
What happens when you remove a value from a numbered PHP array? If I
have an array, [1, 2, 3, 4, 5], I remove 4 from the array, and then
try to access array[3], is it going to give me an error, since I
removed the element with the key 3? Or does PHP do some kind of key
adjusting in such a case?
If you change the ordering of an array (i.e., through a sort or a
shuffle), is the only way to have the indices correspond to the
position to copy the array to a new array using array_values().
http://php.net/manual/en/class.splfixedarray.php
This code:
$arr = array(0,1,2,3,4);
unset($arr[3]);
echo $arr[3]; // undefined index warning, execution continues;
echo isset($arr[3]) ? $arr[3] : '';
print_r($arr);
The print_r() outputs:
Array
(
[0] => 0
[1] => 1
[2] => 2
[4] => 4
)
This depends on the function you choose. Some maintain index association, some do not.
Protip:
Never expect two seemingly-similar PHP functions to behave anything like each other. It's the "English" of programming languages: full of crap stolen from other languages and loads of conventions that contradict each other, but everyone speaks it so hop on board the freedom train.
'murca.
For some reason, I have a sorted php array:
"$arr_questions" = Array [6]
0 Array [6]
1 Array [6]
2 Array [6]
3 Array [6]
4 Array [6]
5 Array [6]
each of the positions is another array. This time it is associative. See position [0]:
0 = Array [6]
question_id 40
question La tercera pregunta del mundo
explanation
choices Array [3]
correct 0
answer 1
Without looping my array, is there any way to access directly this position 0, just knowing one of its properties?
Example... Imagine I have to change some property of the position of the array whose "question_id" property is 40. That is the only I know. I don't know if the question_id property is gonna be in the first or second or which position. And, for example, imagine I want to change the "answer" property to 2.
How can I access directly to that position without looping the whole array. I mean... I don't want to do this:
foreach ($arr_questions as $question){
if ($question["question_id"] == 40){
$question["answer"] == 2;
}
}
A PHP Array lets you access random values by its id.
It is actually a big deal, because in other languages array indices must be always integers.
However, PHP arrays work mostly like other-languages dictionaries, in which your key can be of other data types, like strings.
By that, if you want to be able to access some question, and you know the ID, then you should have constructed the array by letting your question_id be the index of each array entry.
If you can't do that, don't panic.
In the end you will have to make some kind of search, that's true.
But hey, then you have two cases:
a) Your array is big. Wow, in that case, you should run an optimized sorting algorithm, such as mergesort or quicksort, so that you can order your data quickly and then have them already sorted by your wanted field.
b) Your array is not-so-big. I think in that case it's no big deal, and the sorting can slow your application more than it should, and if you want to be quicker, you should cache the results of sorting the questions (if possible) or refactoring the array construction so it uses your wanted key as the array index.
As a side note, you can't map things avoid wasting some CPU time or some RAM space, and usually you can swap one for the other.
I mean, if you store just one array indexed by question_id then you can look up for question_id's in O(1) + O(array-access) time. If O(array-access) is a constant, then you can get to things in O(1). That means constant time, and it is as fast as it can get.
However, if you need other kind of searches you can end up with O(n * log(n)) or O(n²) time complexity.
But, if you had stored as many arrays as ways to order them you should need, you would need only O(1) time to access each of them. But, you would need O(n) space (where n here is the num of features to have direct access to).
That would increment the time to build the arrays (by a constant).
With your situation it's not possible without a loop, but if you change your array structure to this:
array(
39 => array(...),
40 => array(...)
)
Which 39 and 40 are your question_id, then you can access them so fast without any loop.
If you want or have to to keep that structure, then just write a function to get the array, the associative index and the value you want as parameters to search the array and return the found index, so you will not be forced to write this loop over and over ...
No, there is no way to access that element without looping over your array. You might abstract that search into a helper function, however.
This might be a brain fart, since it's a late day, but I'm stuck here.
I need to take a $_POST value from a select box. (It's an array), and convert it to a simple array that doesn't have any keys.
Here's the print_r from the item:
Array ( [0] => 19 [1] => 18 [2] => 21 )
Problem is, I need an array that looks like this:
Array(19,18,21)
Whenever I try to foreach() through the form field, I have to do something like this:
$row[] = $val;
But that leaves me with a numerical index.
What am I missing?
Thanks.
you can't have an array without keys.
Array(19,18,21)
this array has keys 0,1 and 2.
Arrays (in PHP) always have (at least) numeric indices. However, you can extract the values via array_values(). This returns only the values of the given array. It of course has indices, but they are continous and they are numeric. Thats the most simple array representation you can have in PHP.
Update, just to make that clear: You cannot have an array without indices in PHP (as far as I know in any other language thats quite the same), because internaly arrays are always hashmaps and hashmaps always needs a key. The "most common key" are indices. You cannot omit the "keys". On the other side I dont the any reason why one should want it. If you dont want to use the keys, just dont use the keys and thats really all. PHP is quite gentle in this point.
The closest you are going to get is to combine so your keys are your values
array_combine($array1,$array1)
You could try
Array_column(the name of the array, then the positions you want to get).
Then print_r (result)