2014-11-04 103 views
7

有沒有什麼辦法在C#中創建一個變量內聯? 事情是這樣的:TryParse創建內嵌參數?

int x = int.TryParse("5", out new int intOutParameter) ? intOutParameter : 0; 

難道你不認爲這是比外面創建變量更加有用,然後不會再使用它?

+0

可以包裝它在一個私有方法調用? – 2014-11-04 13:56:35

+0

我該怎麼做? – 2014-11-04 14:00:32

回答

12

該語法 - 稱爲聲明表達式 - 位於下一版C#(版本6)的建議功能列表中。

你不是唯一認爲它有用的人。例如,使一個完整的TryParse調用一個表達式(不需要聲明來聲明該變量)。

然而它從has been dropped正在進行的工作到C#6。

我確定我不是唯一一個希望在未來的版本中能夠獲得回報的人。它包括在C#7作爲申報(無需new):

int x = int.TryParse("5", out int intOutParameter) ? intOutParameter : 0; 
+1

我明白了爲什麼現在放棄它 - 雖然需要太多特殊情況或handwavey解析來支持它。 – 2014-11-04 14:06:56

+0

@MatthewWatson更多的情況下,看到F#的模式匹配,並希望做更接近的事情,解決這個(我希望),因此成爲C#7的一部分。 – Richard 2015-06-12 16:54:52

0

基於OP要求:

private static bool IsIntValid(string str) 
{ 
    int i = 0; 
    return int.TryParse(str, out i); 
} 

就算不是最聰明不過的方法,最簡單的我猜: )也可以用擴展方法來包裝這個。

+0

這有點棘手的方式,但感謝解釋。 – 2014-11-04 14:29:57

4

out paraline的內聯聲明是C#中的一項新建議功能,可能是標準的一天,請參閱參考資料。 Probable C# 6.0 features illustrated,部9。預期/建議的語法:

int.TryParse("5", out int x); // this declares (and assigns) a new variable x 

編輯:out變量語法最終在包括C#7.0(Visual Studio中2017);您也可以使用out var x


此外:人們想出了有趣的擴展方法。我試圖讓一個通用的一個:

public delegate bool TryParser<TResult>(string s, out TResult result); 

public static class FunExtensions 
{ 
    public static T TryParse<T>(this string str, TryParser<T> tryParser) 
    { 
    T outResult; 
    tryParser(str, out outResult); 
    return outResult; 
    } 
} 

這可以像這樣使用:

var x = "5".TryParse<int>(int.TryParse); 
    var y = "01/01".TryParse<DateTime>(DateTime.TryParse); 
    var z = "bad".TryParse<decimal>(decimal.TryParse); 

等。我希望編譯器會推斷T從使用中,這樣就可以簡單地說:

var x = "5".TryParse(int.TryParse); // won't compile 

但似乎你必須明確地指定類型參數的方法。

3

作爲一種變通方法,您可以創建一個擴展:

public static int TryParse(this string input, int defaultValue = default(int)) 
{ 
    int intOutParameter; 
    bool parsable = int.TryParse(input, out intOutParameter); 
    if (parsable) 
     return intOutParameter; 
    else 
     return defaultValue; 
} 

然後,你甚至不需要一個out -parameter:

int parsed = "5".TryParse(0); 
+0

棘手的方式來解決問題。 – 2014-11-04 14:19:05

+0

但是如果我想讓這個更通用?我的意思是'Guid.TryParse'和'TimeSpan.TryParse'等。我在我的答案中嘗試了一個通用擴展。 – 2014-11-04 14:25:24

0

你也可以使用一個臨時存儲的所有方法。

public static class Tmp<T> 
{ 
    [ThreadStatic] 
    public static T Value; 
} 

int x = int.TryParse("5", out Tmp<int>.Value) ? Tmp<int>.Value : 0; 
+0

很有意思,但這是否有效? – 2014-11-10 10:50:39

+0

我不明白爲什麼這應該是低效的。沒有對象被創建,只有一個泛型被使用後才被構建。 – IllidanS4 2014-11-10 16:09:16