Лучшие практики: работа с длинными многострочными строками в PHP?

Примечание. Извините, если это очень простой вопрос, но я несколько навязчиво компульсивен относительно форматирования моего кода.

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

class Something
{
    public function getEmailText($vars)
    {
        $text = 'Hello ' . $vars->name . ",

The second line starts two lines below.

I also don't want any spaces before the new line, so it butted up against the left side of the screen.";
        return $text;
    }
}

но он также может быть записан как:

public function getEmailText($vars)
{
    $text = "Hello {$vars->name},\n\rThe second line starts two lines below.\n\rI also don't want any spaces before the new line, so it butted up against the left side of the screen.";
    return $text;
}

но что означает сделка с новыми линиями и каретой? Какая разница? Является ли \n\n эквивалентом \r\r или \n\r? Что я должен использовать, когда создаю разрыв строки между строками?

Затем существует опция буферизации вывода и синтаксис heredoc.

Как вы справляетесь с использованием длинных многострочных строк в ваших объектах?

Ответ 1

Вы должны использовать HEREDOC или NOWDOC.

$var = "some text";
$text = <<<EOT
  Place your text between the EOT. It's
  the delimiter that ends the text
  of your multiline string.
  $var
EOT;

Разница между Heredoc и Nowdoc заключается в том, что PHP-код, встроенный в heredoc, выполняется, а PHP-код в Nowdoc будет распечатан как есть.

$var = "foo";
$text = <<<'EOT'
  My $var
EOT;

В этом случае $text будет иметь значение My $var.

Примечание: перед закрытием EOT; не должно быть пробелов или вкладок. в противном случае вы получите сообщение об ошибке

Ответ 2

Я использую подобную систему как pix0r, и я думаю, что делает код вполне читаемым. Иногда я мог бы дойти до разделения разрывов строк в двойных кавычках и использовать одинарные кавычки для остальной строки. Таким образом, они выделяются из остальной части текста, а переменные также выделяются лучше, если вы используете конкатенацию, а не вводите их внутри строки с двойными кавычками. Поэтому я мог бы сделать что-то подобное с вашим оригинальным примером:

$text = 'Hello ' . $vars->name . ','
      . "\r\n\r\n"
      . 'The second line starts two lines below.'
      . "\r\n\r\n"
      . 'I also don\'t want any spaces before the new line,'
      . ' so it\ butted up against the left side of the screen.';

return $text;

Что касается разрывов строк, с помощью электронной почты вы всегда должны использовать \r\n. PHP_EOL предназначен для файлов, предназначенных для использования в той же операционной системе, в которой работает php.

Ответ 3

Я использую шаблоны для длинного текста:

email-template.txt содержит

hello {name}!
how are you? 

В PHP я делаю это:

$email = file_get_contents('email-template.txt');
$email = str_replace('{name},', 'Simon', $email);

Ответ 4

Добавление \n и/или \r в середине строки, а с очень длинной строкой кода, как во втором примере, не кажется правильным: когда вы читаете код, вы не см. результат, и вам нужно прокрутить страницу.

В таких ситуациях я всегда использую Heredoc (или Nowdoc, если вы используете PHP >= 5.3): легко писать, легко читать, не нуждаться в сверхдолгих строках,...

Например:

$var = 'World';
$str = <<<MARKER
this is a very
long string that
doesn't require
horizontal scrolling, 
and interpolates variables :
Hello, $var!
MARKER;

Только одно: конечный маркер (и ";" после него) должен быть единственной вещью на своей строке: пробел/вкладка до или после!

Ответ 5

Конечно, вы могли бы использовать HEREDOC, но, насколько читаемость кода идет, это действительно не лучше первого примера, обертывая строку на несколько строк.

Если вы действительно хотите, чтобы ваша многострочная строка выглядела хорошо и хорошо сочеталась с вашим кодом, я бы рекомендовал объединить строки вместе:

$text = "Hello, {$vars->name},\r\n\r\n"
    . "The second line starts two lines below.\r\n"
    . ".. Third line... etc";

Это может быть немного медленнее, чем HEREDOC или многострочная строка, но она будет хорошо работать с вашим отступом кода и упростить чтение.

Ответ 6

Мне нравится этот метод немного больше для Javascript, но, похоже, он стоит здесь, потому что он еще не упоминался.

$var = "pizza";

$text = implode(" ", [
  "I love me some",
  "really large",
  $var,
  "pies.",
]);

// "I love me some really large pizza pies."

Для небольших вещей я считаю, что часто бывает проще работать с структурами массива по сравнению с конкатенированными строками.

Связано: impode vs concat performance

Ответ 7

Тот, кто считает, что

"abc\n" . "def\n"

многострочная строка неверна. Это две строки с оператором конкатенации, а не многострочная строка. Такие сцепленные строки нельзя использовать, например, в качестве ключей предопределенных массивов. К сожалению, php не предлагает реальные многострочные строки в виде

"abc\n"
"def\n"

только синтаксис HEREDOC и NOWDOC, который больше подходит для шаблонов, потому что отступ синтаксиса вложенного кода нарушается таким синтаксисом.

Ответ 8

Что касается вашего вопроса о новостях и возвратах каретки:

Я бы рекомендовал использовать предопределенную глобальную константу PHP_EOL, поскольку она решит любые проблемы с совместимостью между платформами.

Этот вопрос был поднят на SO заранее, и вы можете узнать больше информации, прочитав "Когда я использую PHP-константу PHP_EOL"

Ответ 9

а что за дело с новыми линиями и возвратом каретки? Какая разница? Является ли \n\n эквивалентом\r\r или \n\r? Что я должен использовать, когда я создаю разрыв между строками?

Похоже, здесь никто не ответил на этот вопрос, поэтому я здесь.

\r представляет "возврат каретки"

\n представляет "перевод строки"

Истинная причина для них восходит к пишущим машинкам. Когда вы печатаете, "каретка" будет медленно скользить символ за символом вправо от пишущей машинки. Когда вы дойдете до конца линии, вы вернете карету и перейдете на новую линию. Чтобы перейти к новой строке, вы должны щелкнуть рычагом, который подает строки в пишущий тип. Таким образом, эти действия, вместе взятые, назывались переводом строки возврата каретки. Так что буквально

Перевод строки, \n, означает переход к следующей строке.

Возврат каретки, \r, означает перемещение курсора в начало строки.

В конечном итоге Hello\n\nWorld должен привести к следующему выводу на экран:

Hello

     World

Где как Hello\r\rWorld должен привести к следующему выводу.

Только при объединении двух символов \r\n у вас есть общее понимание известной строки. IE Hello\r\nWorld должен привести к:

Hello
World

И, конечно же, \n\r приведет к тому же визуальному выводу, что и \r\n.

Первоначально компьютеры взяли \r и \n в буквальном смысле слова. Однако в наши дни поддержка возврата каретки невелика. Обычно в каждой системе вы можете использовать \n самостоятельно. Это никогда не зависит от ОС, но зависит от того, что вы просматриваете.

Тем не менее, я всегда советую использовать \r\n везде, где вы можете!

Ответ 10

Вы также можете использовать:

<?php
ob_start();
echo "some text";
echo "\n";

// you can also use: 
?> 
some text can be also written here, or maybe HTML:
<div>whatever<\div>
<?php
echo "you can basically write whatever you want";
// and then: 
$long_text = ob_get_clean();