Object.ToString 方法
定義
重要
部分資訊涉及發行前產品,在發行之前可能會有大幅修改。 Microsoft 對此處提供的資訊,不做任何明確或隱含的瑕疵擔保。
傳回代表目前物件的字串。
public:
virtual System::String ^ ToString();
public virtual string ToString ();
public virtual string? ToString ();
abstract member ToString : unit -> string
override this.ToString : unit -> string
Public Overridable Function ToString () As String
傳回
表示目前物件的字串。
備註
Object.ToString是.NET Framework中的主要格式化方法。 它會將物件轉換成其字串表示,使其適合顯示。 (如需.NET Framework中格式化支援的相關資訊,請參閱格式化類型.) 方法的預設 Object.ToString 實作會傳回物件型別的完整名稱。
重要
您可能已遵循另一種類型成員清單的連結來達到此頁面。 這是因為該類型不會覆寫 Object.ToString 。 相反地,它會繼承 方法的功能 Object.ToString 。
類型通常會覆寫 Object.ToString 方法,以提供更適合特定類型的字串表示。 類型也會經常多載 Object.ToString 方法,以支援格式字串或區分文化特性的格式。
本節內容:
預設 Object.ToString () 方法
覆寫 Object.ToString () 方法
多載 ToString 方法
擴充 Object.ToString 方法
Windows 執行階段注意事項
預設 Object.ToString () 方法
方法的預設實作 ToString 會傳回 型 Object 別的完整名稱,如下列範例所示。
using namespace System;
void main()
{
Object^ obj = gcnew Object();
Console::WriteLine(obj->ToString());
}
// The example displays the following output:
// System.Object
Object obj = new Object();
Console.WriteLine(obj.ToString());
// The example displays the following output:
// System.Object
let obj = obj ()
printfn $"{obj.ToString()}"
// printfn $"{obj}" // Equivalent
// The example displays the following output:
// System.Object
Module Example
Public Sub Main()
Dim obj As New Object()
Console.WriteLine(obj.ToString())
End Sub
End Module
' The example displays the following output:
' System.Object
因為 Object 是.NET Framework中所有參考型別的基類,所以不會覆寫 ToString 方法的參考型別繼承此行為。 下列範例將說明這點。 它會定義名為 Object1
的類別,以接受所有 Object 成員的預設實作。 其 ToString 方法會傳回物件的完整型別名稱。
using namespace System;
namespace Examples
{
ref class Object1
{
};
}
void main()
{
Object^ obj1 = gcnew Examples::Object1();
Console::WriteLine(obj1->ToString());
}
// The example displays the following output:
// Examples.Object1
using System;
using Examples;
namespace Examples
{
public class Object1
{
}
}
public class Example
{
public static void Main()
{
object obj1 = new Object1();
Console.WriteLine(obj1.ToString());
}
}
// The example displays the following output:
// Examples.Object1
type Object1() = class end
let obj1 = Object1()
printfn $"{obj1.ToString()}"
// The example displays the following output:
// Examples.Object1
Imports Examples
Namespace Examples
Public Class Object1
End Class
End Namespace
Module Example
Public Sub Main()
Dim obj1 As New Object1()
Console.WriteLine(obj1.ToString())
End Sub
End Module
' The example displays the following output:
' Examples.Object1
覆寫 Object.ToString () 方法
型別通常會覆寫 Object.ToString 方法,以傳回代表物件實例的字串。 例如,基底類型,例如 Char 、 Int32 和 String 提供 ToString 實作,這些實作會傳回 物件所代表值的字串形式。 下列範例會定義類別 Object2
,它會覆寫 ToString 方法以傳回型別名稱及其值。
using namespace System;
ref class Object2
{
private:
Object^ value;
public:
Object2(Object^ value)
{
this->value = value;
}
virtual String^ ToString() override
{
return Object::ToString() + ": " + value->ToString();
}
};
void main()
{
Object2^ obj2 = gcnew Object2(L'a');
Console::WriteLine(obj2->ToString());
}
// The example displays the following output:
// Object2: a
using System;
public class Object2
{
private object value;
public Object2(object value)
{
this.value = value;
}
public override string ToString()
{
return base.ToString() + ": " + value.ToString();
}
}
public class Example
{
public static void Main()
{
Object2 obj2 = new Object2('a');
Console.WriteLine(obj2.ToString());
}
}
// The example displays the following output:
// Object2: a
type Object2(value: obj) =
inherit obj ()
override _.ToString() =
base.ToString() + ": " + value.ToString()
let obj2 = Object2 'a'
printfn $"{obj2.ToString()}"
// The example displays the following output:
// Object2: a
Public Class Object2
Private value As Object
Public Sub New(value As Object)
Me.value = value
End Sub
Public Overrides Function ToString() As String
Return MyBase.ToString + ": " + value.ToString()
End Function
End Class
Module Example
Public Sub Main()
Dim obj2 As New Object2("a"c)
Console.WriteLine(obj2.ToString())
End Sub
End Module
' The example displays the following output:
' Object2: a
下表列出 .NET 中的類型類別,並指出是否覆寫 Object.ToString 方法。
型別分類 | Overrides Object.ToString () | 行為 |
---|---|---|
類別 | n/a | n/a |
結構 | 是 (ValueType.ToString) | 與 Object.ToString() 相同 |
列舉型別 | 是 (Enum.ToString()) | 成員名稱 |
介面 | 否 | n/a |
代理人 | 否 | n/a |
如需覆寫 的其他資訊,請參閱一 ToString 節。
多載 ToString 方法
除了覆寫無 Object.ToString() 參數方法之外,許多類型都會多載 ToString
方法,以提供接受參數的方法版本。 最常見的做法是提供變數格式設定和區分文化特性的格式設定的支援。
下列範例會 ToString
多載 方法,以傳回包含類別各種欄位 Automobile
值的結果字串。 它會定義四種格式字串:G,它會傳回模型名稱和年份;D,傳回模型名稱、年份和門數;C,傳回模型名稱、年份和圓柱數;和 A,會傳回所有四個域值的字串。
using System;
public class Automobile
{
private int _doors;
private string _cylinders;
private int _year;
private string _model;
public Automobile(string model, int year , int doors,
string cylinders)
{
_model = model;
_year = year;
_doors = doors;
_cylinders = cylinders;
}
public int Doors
{ get { return _doors; } }
public string Model
{ get { return _model; } }
public int Year
{ get { return _year; } }
public string Cylinders
{ get { return _cylinders; } }
public override string ToString()
{
return ToString("G");
}
public string ToString(string fmt)
{
if (string.IsNullOrEmpty(fmt))
fmt = "G";
switch (fmt.ToUpperInvariant())
{
case "G":
return string.Format("{0} {1}", _year, _model);
case "D":
return string.Format("{0} {1}, {2} dr.",
_year, _model, _doors);
case "C":
return string.Format("{0} {1}, {2}",
_year, _model, _cylinders);
case "A":
return string.Format("{0} {1}, {2} dr. {3}",
_year, _model, _doors, _cylinders);
default:
string msg = string.Format("'{0}' is an invalid format string",
fmt);
throw new ArgumentException(msg);
}
}
}
public class Example
{
public static void Main()
{
var auto = new Automobile("Lynx", 2016, 4, "V8");
Console.WriteLine(auto.ToString());
Console.WriteLine(auto.ToString("A"));
}
}
// The example displays the following output:
// 2016 Lynx
// 2016 Lynx, 4 dr. V8
open System
type Automobile(model: string, year: int, doors: int, cylinders: string) =
member _.Doors = doors
member _.Model = model
member _.Year = year
member _.Cylinders = cylinders
override this.ToString() =
this.ToString "G"
member _.ToString(fmt) =
let fmt =
if String.IsNullOrEmpty fmt then "G"
else fmt.ToUpperInvariant()
match fmt with
| "G" ->
$"{year} {model}"
| "D" ->
$"{year} {model}, {doors} dr."
| "C" ->
$"{year} {model}, {cylinders}"
| "A" ->
$"{year} {model}, {doors} dr. {cylinders}"
| _ ->
raise (ArgumentException $"'{fmt}' is an invalid format string")
let auto = Automobile("Lynx", 2016, 4, "V8")
printfn $"{auto}"
printfn $"""{auto.ToString "A"}"""
// The example displays the following output:
// 2016 Lynx
// 2016 Lynx, 4 dr. V8
Public Class Automobile
Private _doors As Integer
Private _cylinders As String
Private _year As Integer
Private _model As String
Public Sub New(model As String, year As Integer, doors As Integer,
cylinders As String)
_model = model
_year = year
_doors = doors
_cylinders = cylinders
End Sub
Public ReadOnly Property Doors As Integer
Get
Return _doors
End Get
End Property
Public ReadOnly Property Model As String
Get
Return _model
End Get
End Property
Public ReadOnly Property Year As Integer
Get
Return _year
End Get
End Property
Public ReadOnly Property Cylinders As String
Get
Return _cylinders
End Get
End Property
Public Overrides Function ToString() As String
Return ToString("G")
End Function
Public Overloads Function ToString(fmt As String) As String
If String.IsNullOrEmpty(fmt) Then fmt = "G"
Select Case fmt.ToUpperInvariant()
Case "G"
Return String.Format("{0} {1}", _year, _model)
Case "D"
Return String.Format("{0} {1}, {2} dr.",
_year, _model, _doors)
Case "C"
Return String.Format("{0} {1}, {2}",
_year, _model, _cylinders)
Case "A"
Return String.Format("{0} {1}, {2} dr. {3}",
_year, _model, _doors, _cylinders)
Case Else
Dim msg As String = String.Format("'{0}' is an invalid format string",
fmt)
Throw New ArgumentException(msg)
End Select
End Function
End Class
Module Example
Public Sub Main()
Dim auto As New Automobile("Lynx", 2016, 4, "V8")
Console.WriteLine(auto.ToString())
Console.WriteLine(auto.ToString("A"))
End Sub
End Module
' The example displays the following output:
' 2016 Lynx
' 2016 Lynx, 4 dr. V8
下列範例會呼叫多載 Decimal.ToString(String, IFormatProvider) 方法,以顯示貨幣值的區分文化特性格式。
using System;
using System.Globalization;
public class Example
{
public static void Main()
{
string[] cultureNames = { "en-US", "en-GB", "fr-FR",
"hr-HR", "ja-JP" };
Decimal value = 1603.49m;
foreach (var cultureName in cultureNames) {
CultureInfo culture = new CultureInfo(cultureName);
Console.WriteLine("{0}: {1}", culture.Name,
value.ToString("C2", culture));
}
}
}
// The example displays the following output:
// en-US: $1,603.49
// en-GB: £1,603.49
// fr-FR: 1 603,49 €
// hr-HR: 1.603,49 kn
// ja-JP: ¥1,603.49
open System.Globalization
let cultureNames =
[| "en-US"; "en-GB"; "fr-FR"; "hr-HR"; "ja-JP" |]
let value = 1603.49m
for cultureName in cultureNames do
let culture = CultureInfo cultureName
printfn $"""{culture.Name}: {value.ToString("C2", culture)}"""
// The example displays the following output:
// en-US: $1,603.49
// en-GB: £1,603.49
// fr-FR: 1 603,49 €
// hr-HR: 1.603,49 kn
// ja-JP: ¥1,603.49
Imports System.Globalization
Module Example
Public Sub Main()
Dim cultureNames() As String = { "en-US", "en-GB", "fr-FR",
"hr-HR", "ja-JP" }
Dim value As Decimal = 1603.49d
For Each cultureName In cultureNames
Dim culture As New CultureInfo(cultureName)
Console.WriteLine("{0}: {1}", culture.Name,
value.ToString("C2", culture))
Next
End Sub
End Module
' The example displays the following output:
' en-US: $1,603.49
' en-GB: £1,603.49
' fr-FR: 1 603,49 €
' hr-HR: 1.603,49 kn
' ja-JP: ¥1,603.49
如需格式化字串和區分文化特性格式的詳細資訊,請參閱 格式化類型。 如需數值所支援的格式字串,請參閱 標準數值格式字串 和 自訂數值格式字串。 如需日期和時間值所支援的格式字串,請參閱 標準日期和時間格式字串 和 自訂日期和時間格式字串。
擴充 Object.ToString 方法
因為類型會繼承預設 Object.ToString 方法,所以您可能會發現其行為不想要,而且想要變更它。 這特別適用于陣列和集合類別。 雖然您可能會預期 ToString
陣列或集合類別的 方法顯示其成員的值,但會改為顯示類型完整型別名稱,如下列範例所示。
int[] values = { 1, 2, 4, 8, 16, 32, 64, 128 };
Console.WriteLine(values.ToString());
List<int> list = new List<int>(values);
Console.WriteLine(list.ToString());
// The example displays the following output:
// System.Int32[]
// System.Collections.Generic.List`1[System.Int32]
let values = [| 1; 2; 4; 8; 16; 32; 64; 128 |]
printfn $"{values}"
let list = ResizeArray values
printfn $"{list}"
// The example displays the following output:
// System.Int32[]
// System.Collections.Generic.List`1[System.Int32]
Imports System.Collections.Generic
Module Example
Public Sub Main()
Dim values() As Integer = { 1, 2, 4, 8, 16, 32, 64, 128 }
Console.WriteLine(values.ToString())
Dim list As New List(Of Integer)(values)
Console.WriteLine(list.ToString())
End Sub
End Module
' The example displays the following output:
' System.Int32[]
' System.Collections.Generic.List`1[System.Int32]
您有數個選項可產生您想要的結果字串。
如果類型是陣列、集合物件或實作 IEnumerable 或 IEnumerable<T> 介面的物件,您可以使用 C#
For Each...Next
中的 語句或 Visual Basic 中的 建構來列舉其元素foreach
。如果類別不是
sealed
在 C# ) 中 (,或NotInheritable
是在 Visual Basic) 中 (,您可以開發繼承自要自訂其方法之基類的包裝函式類別 Object.ToString 。 這至少需要您執行下列動作:實作任何必要的建構函式。 衍生類別不會繼承其基類建構函式。
Object.ToString覆寫 方法以傳回您想要的結果字串。
下列範例會定義 類別的 List<T> 包裝函式類別。 它會覆寫 Object.ToString 方法,以顯示集合中每個方法的值,而不是完整型別名稱。
using System; using System.Collections.Generic; public class CList<T> : List<T> { public CList(IEnumerable<T> collection) : base(collection) { } public CList() : base() {} public override string ToString() { string retVal = string.Empty; foreach (T item in this) { if (string.IsNullOrEmpty(retVal)) retVal += item.ToString(); else retVal += string.Format(", {0}", item); } return retVal; } } public class Example { public static void Main() { var list2 = new CList<int>(); list2.Add(1000); list2.Add(2000); Console.WriteLine(list2.ToString()); } } // The example displays the following output: // 1000, 2000
open System open System.Collections.Generic type CList<'T>() = inherit ResizeArray<'T>() override this.ToString() = let mutable retVal = String.Empty for item in this do if String.IsNullOrEmpty retVal then retVal <- retVal + string item else retVal <- retVal + $", {item}" retVal let list2 = CList() list2.Add 1000 list2.Add 2000 printfn $"{list2}" // The example displays the following output: // 1000, 2000
Imports System.Collections.Generic Public Class CList(Of T) : Inherits List(Of T) Public Sub New(capacity As Integer) MyBase.New(capacity) End Sub Public Sub New(collection As IEnumerable(Of T)) MyBase.New(collection) End Sub Public Sub New() MyBase.New() End Sub Public Overrides Function ToString() As String Dim retVal As String = String.Empty For Each item As T In Me If String.IsNullOrEmpty(retval) Then retVal += item.ToString() Else retval += String.Format(", {0}", item) End If Next Return retVal End Function End Class Module Example Public Sub Main() Dim list2 As New CList(Of Integer) list2.Add(1000) list2.Add(2000) Console.WriteLine(list2.ToString()) End Sub End Module ' The example displays the following output: ' 1000, 2000
開發 擴充方法 ,以傳回您想要的結果字串。 請注意,您無法以這種方式覆寫預設 Object.ToString 方法, (也就是說,在 C#) 或模組 (中的擴充類別 ( (Visual Basic) 不能有名為
ToString
的無參數方法,以取代原始類型ToString
的方法。 您必須為無ToString
參數取代提供一些其他名稱。下列範例會定義兩個擴充 List<T> 類別的方法:無
ToString2
參數方法,以及ToString
具有 String 代表格式字串之參數的方法。using System; using System.Collections.Generic; public static class StringExtensions { public static string ToString2<T>(this List<T> l) { string retVal = string.Empty; foreach (T item in l) retVal += string.Format("{0}{1}", string.IsNullOrEmpty(retVal) ? "" : ", ", item); return string.IsNullOrEmpty(retVal) ? "{}" : "{ " + retVal + " }"; } public static string ToString<T>(this List<T> l, string fmt) { string retVal = string.Empty; foreach (T item in l) { IFormattable ifmt = item as IFormattable; if (ifmt != null) retVal += string.Format("{0}{1}", string.IsNullOrEmpty(retVal) ? "" : ", ", ifmt.ToString(fmt, null)); else retVal += ToString2(l); } return string.IsNullOrEmpty(retVal) ? "{}" : "{ " + retVal + " }"; } } public class Example { public static void Main() { List<int> list = new List<int>(); list.Add(1000); list.Add(2000); Console.WriteLine(list.ToString2()); Console.WriteLine(list.ToString("N0")); } } // The example displays the following output: // { 1000, 2000 } // { 1,000, 2,000 }
open System open System.Collections.Generic type List<'T> with member this.ToString2<'T>() = let mutable retVal = String.Empty for item in this do retVal <- retVal + $"""{if String.IsNullOrEmpty retVal then "" else ", "}{item}""" if String.IsNullOrEmpty retVal then "{}" else "{ " + retVal + " }" member this.ToString<'T>(fmt: string) = let mutable retVal = String.Empty for item in this do match box item with | :? IFormattable as ifmt -> retVal <- retVal + $"""{if String.IsNullOrEmpty retVal then "" else ", "}{ifmt.ToString(fmt, null)}""" | _ -> retVal <- retVal + this.ToString2() if String.IsNullOrEmpty retVal then "{}" else "{ " + retVal + " }" let list = ResizeArray() list.Add 1000 list.Add 2000 printfn $"{list.ToString2()}" printfn $"""{list.ToString "N0"}""" // The example displays the following output: // { 1000, 2000 } // { 1,000, 2,000 }
Imports System.Collections.Generic Imports System.Runtime.CompilerServices Public Module StringExtensions <Extension()> Public Function ToString2(Of T)(l As List(Of T)) As String Dim retVal As String = "" For Each item As T In l retVal += String.Format("{0}{1}", If(String.IsNullOrEmpty(retVal), "", ", "), item) Next Return If(String.IsNullOrEmpty(retVal), "{}", "{ " + retVal + " }") End Function <Extension()> Public Function ToString(Of T)(l As List(Of T), fmt As String) As String Dim retVal As String = String.Empty For Each item In l Dim ifmt As IFormattable = TryCast(item, IFormattable) If ifmt IsNot Nothing Then retVal += String.Format("{0}{1}", If(String.IsNullOrEmpty(retval), "", ", "), ifmt.ToString(fmt, Nothing)) Else retVal += ToString2(l) End If Next Return If(String.IsNullOrEmpty(retVal), "{}", "{ " + retVal + " }") End Function End Module Module Example Public Sub Main() Dim list As New List(Of Integer) list.Add(1000) list.Add(2000) Console.WriteLine(list.ToString2()) Console.WriteLine(list.ToString("N0")) End Sub End Module ' The example displays the following output: ' { 1000, 2000 } ' { 1,000, 2,000 }
Windows 執行階段注意事項
當您在Windows 執行階段中的類別上呼叫 ToString 方法時,它會為未覆寫 ToString 的類別提供預設行為。 這是.NET Framework為Windows 執行階段 (提供支援的一部分,請參閱.NET Framework Windows 市集應用程式和Windows 執行階段) 的支援。 Windows 執行階段中的類別不會繼承 Object ,而且不一定實作 ToString 。 不過,當您在 C# 或Visual Basic程式碼中使用 、 和 方法時,它們一律會出現 ToString 、 Equals(Object) 和 GetHashCode 方法,而.NET Framework會提供這些方法的預設行為。
從 .NET Framework 4.5.1 開始,Common Language Runtime 會在 Windows 執行階段 物件上使用IStringable.ToString,然後再回到 的預設實作 Object.ToString 。
注意
Windows 執行階段以 C# 或Visual Basic撰寫的類別可以覆寫 ToString 方法。
Windows 執行階段和 IStringable 介面
從Windows 8.1開始,Windows 執行階段包含IStringable介面,其單一方法IStringable.ToString提供與 所提供的 Object.ToString 相同基本格式支援。 若要避免模棱兩可,您不應該在 Managed 類型上實作 IStringable 。
當 Managed 物件是由機器碼或以 JavaScript 或 C++/CX 等語言撰寫的程式碼呼叫時,它們似乎會實作 IStringable。 如果 Managed 物件上未實作IStringable,Common Language Runtime 會自動將呼叫從IStringable.ToString路由傳送至 Object.ToString 。
警告
由於 Common Language Runtime 會自動針對 Windows Store 應用程式中的所有受控類型實作IStringable,因此建議您不要提供自己的 IStringable
實作。 從 Windows 執行階段、C++/CX 或 JavaScript 呼叫 ToString
時,實作 IStringable
可能會導致非預期的行為。
如果您選擇在匯出Windows 執行階段元件中的公用 Managed 類型中實作IStringable,則適用下列限制:
您只能在「類別實作」關聯性中定義 IStringable 介面,如下所示:
public class NewClass : IStringable
Public Class NewClass : Implements IStringable
您無法在介面上實作 IStringable 。
您無法將參數宣告為 IStringable類型。
IStringable 不能是方法、屬性或欄位的傳回型別。
您無法使用如下所示的方法定義,從基類隱藏 IStringable 實作:
public class NewClass : IStringable { public new string ToString() { return "New ToString in NewClass"; } }
相反地, IStringable.ToString 實作必須一律覆寫基類實作。 您只能藉由針對強型別類別執行個體叫用
ToString
實作來隱藏該實作。
請注意,在各種情況下,從機器碼呼叫到實作 IStringable 或隱藏 其 ToString 實作的 Managed 類型,可能會產生非預期的行為。
給繼承者的注意事項
當您實作自己的類型時,您應該覆寫 ToString() 方法,以傳回這些類型有意義的值。 需要更充分控制格式設定的衍生類別,比 ToString() 提供的 可以實作 IFormattable 介面。 其 ToString(String, IFormatProvider) 方法可讓您定義可控制格式設定的格式字串,以及使用 IFormatProvider 可為特定文化特性格式設定提供的物件。
方法的 ToString() 覆寫應遵循下列指導方針:
傳回的字串應該是人類易記且可讀的。
傳回的字串應該唯一識別物件實例的值。
傳回的字串應該盡可能短,以便偵錯工具適合顯示。
您的 ToString() 覆寫不應該傳回 Empty 或 Null 字串。
您的 ToString() 覆寫不應該擲回例外狀況。
如果實例的字串表示區分文化特性,或可以多種方式格式化,請實作 IFormattable 介面。
如果傳回的字串包含敏感性資訊,您應該先要求適當的許可權。 如果需求成功,您可以傳回敏感性資訊;否則,您應該傳回排除敏感性資訊的字串。
您的 ToString() 覆寫應該沒有任何可觀察的副作用,以避免偵錯時發生複雜問題。 例如,對 方法的 ToString() 呼叫不應該變更實例欄位的值。
如果您的型別實作剖析方法 (或 方法
Parse
TryParse
、建構函式或其他靜態方法,以從字串) 具現化型別的實例,您應該確定方法傳 ToString() 回的字串可以轉換成物件實例。