2011-02-02 1 views
2

При использовании построителя строк я получаю ожидаемые результаты от функций добавления и добавления строк при использовании перечисления - это вход, но когда перечисление вставляется в бокс, добавьте строку и добавьте функцию разные результаты.StringBuilder Append и AppendLine дают разные результаты для Enum

Может ли кто-нибудь сказать мне, что может быть за этим?

выход Код:

Append Enum: 1 
Append Enum To String: One 
Append Line Enum: 1 
Append Line Enum To String: One 
Append Object: One 
Append Object To String: One 
Append Line Object: 1 
Append Line Object To String: One 

Код:

Public Enum eTest 
    One = 1 
    Two = 2 
End Enum 

Sub Main() 
    Dim sb As New System.Text.StringBuilder() 
    Dim x = eTest.One 
    sb.Append("Append Enum: ").Append(x).AppendLine() 
    sb.Append("Append Enum To String: ").Append(x.ToString()).AppendLine() 
    sb.Append("Append Line Enum: ").AppendLine(x) 
    sb.Append("Append Line Enum To String: ").AppendLine(x.ToString()) 

    Dim o As Object = x 
    sb.Append("Append Object: ").Append(o).AppendLine() 
    sb.Append("Append Object To String: ").Append(o.ToString()).AppendLine() 
    sb.Append("Append Line Object: ").AppendLine(o) 
    sb.Append("Append Line Object To String: ").AppendLine(o.ToString()) 

    Console.WriteLine(sb.ToString()) 


    '=============================== 
    Console.ReadKey() 
End Sub 
+0

Положите опцию Strict On в верхней части файла, чтобы избавиться от разницы. –

ответ

6

Эта линия

sb.Append("Append Object: ").Append(o).AppendLine() 

вызывает o.ToString() быть приложен к экземпляру StringBuilder и разница. Конечно, этот вызов просто проходит через экземпляр вашего перечисления в коробке, и именно поэтому вы видите One для этого вызова.

Это связано с тем, что вы вызываете перегрузку StringBuilder.Append(object), которая будет просто вызывать o.ToString() на переданном экземпляре объекта. Это явно в документации:

Метод Append вызывает метод Object.ToString, чтобы получить строковое представление value. Если value - null, никаких изменений в объекте StringBuilder.

С другой стороны, когда вы звоните

sb.Append("Append Enum: ").Append(x).AppendLine() 

где x является экземпляр перечисления, x будет неявно преобразован в экземпляр int, который будет вызывать перегрузку StringBuilder.Append(int).

Обратите внимание, что это относится к VB.NET. C# не будет неявно конвертировать x в int при выборе перегрузки StringBuilder.Append для вызова; он будет вызывать StringBuilder.Append(object).

+0

Эта часть, на мой взгляд, я в порядке, любопытная часть для меня - это разница в выходе .Append (o) и .AppendLine (o), которая испускает «Один» и «1» соответственно. Я ожидаю, что вызов обеих функций с объектом в коробке даст тот же результат. –

+2

Это VB.NET. Есть только две перегрузки 'StringBuilder.AppendLine'. Первый - это «AppendLine()», а второй - «AppendLine (string)». Первый здесь не применим. Таким образом, это первое, что применяется. Итак, теперь мы передаем переменную, объявленную как «объект», методу, получающему параметр типа 'string'. VB.NET добавит вызов 'Microsoft.VisualBasic.CompilerServices.Conversions.ToString (object)', который обнаружит, что 'o' конвертируется в экземпляр' Int32' и затем вызывает 'Int32.ToString'. Добавьте «Option Strict On», и этого не произойдет. Это также не происходит в C#. – jason

+0

Коррекция. Изменить «Первый не может применяться здесь, поэтому он применяется первым». к «Первое не может применяться здесь. Таким образом, это второе действие». – jason