манипулирование строками в верхнем и нижнем регистре в переполнении стека

Мне задали этот вопрос в недавнем интервью.
Строка содержит a-z, A-Z и пробелы. Сортируйте строку так, чтобы все нижние регистры были в начале, пробелы в среднем и верхнем регистре в конце. Первоначальный порядок в нижнем и верхнем регистре должен оставаться неизменным. Вот что я придумал:

$str = "wElComE to CaLiFOrNiA";

$lowercase ="";
$uppercase="";
$spaces="";

for ($i=0 ; $i <= strlen($str)-1 ; $i++)
{
if ($str[$i] <= 'z' && $str[$i] >= 'a'  )
{
$lowercase .=$str[$i];
}

else if (($str[$i] <= 'Z' && $str[$i] >= 'A'))
{
$uppercase .=$str[$i];
}
else
{
$spaces.=$str[$i];
}
}
echo $lowercase.$spaces.$uppercase;

input: wElComE to CaLiFOrNiA
output: wlomtoairi ECECLFONA

Мне интересно, есть ли лучшие способы сделать это? И во входной строке есть 2 пробела, а на выходе отображается только один пробел. Сложность этого права O (N).

Есть идеи?

0

Решение

Я уверен, что есть много способов сделать это. Вы можете сделать это с помощью регулярных выражений ..

$str = "wElComE to CaLiFOrNiA";
preg_match_all('~([a-z])~', $str, $lowercase);
preg_match_all('~([A-Z])~', $str, $uppercase);
preg_match_all('~(\h)~', $str, $spaces);
echo implode('', $lowercase[1]) . implode('', $spaces[1]) . implode('', $uppercase[1]);

Выход:

wlomtoairi  ECECLFONA

Когда ты сказал better Вы имеете в виду производительность, читабельность или что-то еще?

Подход второго регулярного выражения:

$str = "wElComE to CaLiFOrNiA";
echo preg_replace('~[^a-z]~', '', $str) . preg_replace('~[^\h]~', '', $str) . preg_replace('~[^A-Z]~', '', $str);
1

Другие решения

Я думаю, что ваше решение довольно хорошо, но если вы занимаетесь микрооптимизацией, вы можете внести некоторые незначительные изменения. Следующее выполняется быстрее, чем описанные выше решения с регулярными выражениями (тест производительности 10000 раз), по крайней мере, в моей системе:

$str = "wElComE to CaLiFOrNiA";
$lowercase = "";
$uppercase = "";
$spaces    = "";

$end = strlen($str); // Calculate length just once
for ($i = 0; $i < $end; $i++) {
$c = $str[$i]; // Get $str[$i] once

// We know there are only A-Z, a-z and space chars so we
// only need a greater-than check ('a' > 'A' > ' ')
if ($c >= 'a') {
$lowercase .= $c;
} else if ($c >= 'A') {
$uppercase .= $c;
} else
$spaces .= $c;
}
echo $lowercase . $spaces . $uppercase, PHP_EOL;
0

function sortString($string)
{
$string_chars = str_split($string);

$output = ['', '', ''];

foreach ($string_chars as $char) {
$output[$char === ' ' ? 1 : ($char === ucfirst($char) ? 2 : 0)] .= $char;
}

return implode('', $output);
}

echo sortString("wElComE to CaLiFOrNiA");

дает wlomtoairi ECECLFONA

0
По вопросам рекламы [email protected]