You should simply sort array descending with key length and it will both for numbers and other strings. The following code should work for you:
<?php
$text = 'I have 10 (or 21) apples and I would like to bake an apple pie';
$numbers = array(0, 1, 2, 10, 21, ' a ', ' an ');
$letters = array('zero', 'one', 'two','ten','twenty one',' A ',' AN ');
$data = array_combine($numbers, $letters);
krsort($data, SORT_STRING);
echo str_replace(array_keys($data), array_values($data), $text);
// Output: I have ten (or twenty one) apples and I would like to bake AN apple pie
?>
EDIT
For the following input data:
$text = 'An 1 Anha 2 Anh 21';
$numbers = array(0, 1, 2, 10, 21, ' a ', ' an ', 'An','Anh', 'Anha');
$letters = array('zero', 'one', 'two','ten','twenty one',' A ',' AN ', 'Hi', 'Hello', 'Bye');
$data = array_combine($numbers, $letters);
krsort($data, SORT_STRING);
echo str_replace(array_keys($data), array_values($data), $text);
using the same method will give you:
Hi one Bye two Hello twenty one
output as intended
How does it work - explanation
With array_combine()
function you create one new array, that have keys from $numbers
array and values from $letters
. This function is used only because input data in 2 separate arrays. If there were used associative array at the beginning: $data[0] => 'zero'; ... $data[1] => 'one';, ....
this function would be unnecessary.
Now because some keys may contain other keys, you need to sort your data that way that you have the longest keys before shorter ones. It makes that 10
will be changed into ten
and not one zero
. You can use for that krsort()
function that sorts array using keys for compare (using array_combine our keys are now data from $numbers
array) in reverse order using SORT_STRING
comparison so if we have words c, a, ccc and cc
it will sort it in reverse other (normal other is a, c, cc, ccc
) so they will be ccc, cc, c, a
.
At last after sorting, we need to pass data to str_replace
. This function needs keys and values and we don't have them separate because earlier we created one array using array_combine()
and sort it. But we can now get keys and values from that array using array_keys()
and array_values()
functions.