Строки интерполяции длинной строки в C # 6


134

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

var str = string.Format("some text {0} more text {1}",
    obj1.property,
    obj2.property);

У кого-нибудь есть какие-нибудь предпочтительные способы разбить эти строки?

Я полагаю, вы могли бы сделать что-то вроде:

var str = $"some text { obj1.property }" +
  " more text { obj2.property };

1
По моему опыту, лучше избегать интерполяции сложных выражений. В этом случае лучше извлечь переменную. Если вы это сделаете, и вы разбиваете, где у вас есть новые строки внутри ваших строк, это обычно подходит.
markijbema

2
Меня смущает этот вопрос. Я просто хочу многострочную, $""которая работает как@""
Полковник Паник

2
Полковник Панич, вопрос заключается в том, как разбить длинные строки интерполяции, чтобы мы не нарушали требования к ширине столбцов, не вводя перевод строки в сам строковый литерал. $ @ "" отлично, но любые символы новой строки, введенные в него, будут в строковом литерале.
Джеремайя Гоуди

4
Опасность: $"some text { obj1.property }" + " more text { obj2.property }";не делает того, что вы думаете. Только первая половина этого выражения является интерполированной строкой; он затем объединяется с , не -interpolated строка буквального" more text { obj2.property }"
Bacar

1
Для поддержки \ t \ r \ n в $ @ см. Вопрос stackoverflow.com/questions/51991713/…
Хассан

Ответы:


198

Вы можете разбить строку на несколько строк, но я бы не сказал, что синтаксис выглядит красиво.

Вам нужно использовать $@синтаксис для использования интерполированной дословной строки, и вы можете помещать символы новой строки внутри {...}параметров, например:

string s = $@"This is all {
    10
    } going to be one long {
    DateTime.Now
    } line.";

Вышеупомянутая строка не будет содержать никаких символов новой строки и фактически будет иметь такое содержимое:

Это все 10 будет одной длинной строкой 01.08.2015 23.49.47.

(примечание, норвежский формат)

Теперь, сказав это, я бы не перестал употреблять string.Format. На мой взгляд, некоторые из этих выражений строковой интерполяции выглядят действительно хорошо, но более сложные из них начинают становиться очень трудными для чтения. Учитывая, что, если вы не используете FormattableString, код в String.Formatлюбом случае будет скомпилирован в вызов , я бы сказал, продолжайте идти String.Formatтуда, где это имеет смысл.


Твердый ответ. Я почти уверен FormattableString, что это String.Formatтоже сводится к звонку .
Алекс Букер

8
Этот ответ помог мне понять, как сделать прямо противоположное. Спасибо за $@""синтаксис!
Бобсон,

@AlexBooker Это сложнее. Вы не можете этого сделать, FormattableString.Invarian($"Hello {name}" + \n "are you the owner of {pet}?");потому что он объединяет две интерполированные строки в одну простую строку.
ANeves

Новые строки и табуляции учитываются в интерполированных дословных строках. Введите следующее в интерактивное окно C #, и результирующая строка будет отформатирована :. > var name = "Simon"; var templateName = "How to interpolate a verbatim string"; var now = DateTime.UtcNow;. var output = $@"Hi {name}, This template is a demo of {templateName}. It was ran at {now.ToString("o")}"; > output, На выходе получается"Hi Simon,\r\nThis template is a demo of How to interpolate a verbatim string.\r\n\r\nIt was ran at 2020-01-24T15:49:35.6678353Z"
Enzoaeneas

1
@Enzoaeneas Я думаю, вы переоценили поддержку форматирования в комментариях, но я понимаю и согласен с тем, что вы говорите.
Лассе В. Карлсен,

61

Вы можете комбинировать $и @вместе, чтобы получить строковую интерполяцию и многострочный строковый литерал:

var str = $@"some text { obj1.property }
     more text { obj2.property }";

Но это даст вам NewLineпромежуточный персонаж, так что это может быть не то, что вам нужно.


3
Но разве @ не помещает перевод строки в литерал?
Джеремайя Гоуди,

5
Оно делает. Обновил мой ответ, чтобы прямо сказать это.
MarcinJuraszek

Не только новая строка, но и начальная вкладка (и) новой строки. Чтобы правильно отобразить фактический формат строки при использовании $@"в Visual Studio, вы должны начинать каждую новую строку с левого края текстового редактора.
GDS

С помощью этого решения вы не можете использовать, например, \ r и \ n в строке
Johan Franzén

22

Хотя OP просил что-то еще, я ожидаю, что многие люди, читающие этот вопрос, захотят, чтобы многострочный интерполированный $"", работающий как @"". Для этого используйте$@""

$@"Height: {height}
Width: {width}
Background: {background}"

3
Ему не нужны символы новой строки в выводе, только сам код переносится на разные строки
Мартин Каподичи

7
Он пояснил, что этот ответ предназначен для аудитории, которая приходит в поисках того, как создавать многострочные строки с использованием синтаксиса интерполяции строк.
Брэндон Бондс

2

Это оно:

var str = $"some text { obj1.property }" +
          $" more text { obj2.property }";

Обратите внимание на второе $в$"..." + $"..."


18
Обратите внимание, что это вызовет два вызова String.Format, а также создаст три строки в памяти (сторона A, сторона B и A + B)
Кевин Калитовски

1
Разве это не помешало бы вам использовать FormattableStringприведение к объединенной строке?
binki

4
Сегодня во многих реализациях, работающих на ЦП с тактовой частотой ГГц и Гб памяти, дополнительный вызов и дополнительная строка не вызовут проблем с производительностью. Проблемы с производительностью будут вызваны, например, использованием алгоритма O (n2). Я считаю несправедливым голосовать против этого парня.
Johan Franzén

1

В качестве примера я использовал StringBuilder в переопределенном ToString ().

    // return employee data
    public override string ToString()
    {
        StringBuilder buffer = new StringBuilder();
        buffer.AppendLine($"Number: {EmployeeNumber}");
        buffer.AppendLine($"Name: {EmployeeName}");
        buffer.AppendLine($"Address: {PostalAddress}");
        buffer.AppendLine($"Phone: {PhoneNumber}");
        buffer.AppendLine($"Age: {EmployeeAge}");
        buffer.AppendLine($"Gender: {EmployeeGender}");
        buffer.AppendLine($"Status: {EmployeeStatus}");
        buffer.AppendLine($"Manager: {EmployeeManager}");
        buffer.AppendLine($"Start: {EmployeeStartDate.ToShortDateString()}");
        return buffer.ToString();
    }

тогда почему бы и нет buffer.AppendFormat("{0}Number: {1}", Environment.NewLine, EmployeeNumber);???
TS
Используя наш сайт, вы подтверждаете, что прочитали и поняли нашу Политику в отношении файлов cookie и Политику конфиденциальности.
Licensed under cc by-sa 3.0 with attribution required.