2011-12-19 14 views
1

私は自分のページに改ページを作成しようとしています。ユーザーはページごとに表示される項目の数を選択できます。次に、推奨サイズがCookieとして保存されます。しかし、クエリーストリングのパラメータとクッキーのどちらかを選択しようとすると、エラーが発生しました:ASP.NET MVC/C#の - ヌル合体演算子、タイプ

public ActionResult Index(string keyword, int? page, int? size) 
    { 
     keyword = keyword ?? ""; 
     page = page ?? 1; 

     //Operator "??" cannot be applied to operands of type "int" and "int" 
     size = size ?? Convert.ToInt32(Request.Cookies.Get("StoriesPageSize").Value) ?? 10; 

このエラーの原因は何ですか?それを修正するには?

+0

関連:http://stackoverflow.com/questions/7729024/asp-net-mvc-razor-ternary –

答えて

6

Convert.ToInt32だけint、ないint?返します - ので、表現の種類:

size ?? Convert.ToInt32(...) 

はタイプ intです。ヌル合体演算子式の最初のオペランドとしてヌル値を持たない値型を使用することはできません。ヌルにすることはできません。したがって、2番目のオペランド(この場合は10)は決して使用できません。

public ActionResult Index(string keyword, int? page, int? size) 
{ 
    keyword = keyword ?? ""; 
    page = page ?? 1; 

    size = size ?? GetSizeFromCookie() ?? 10; 
} 

private int? GetSizeFromCookie() 
{ 
    string cookieValue = Request.Cookies.Get("StoriesPageSize").Value; 
    if (cookieValue == null) 
    { 
     return null; 
    } 
    int size; 
    if (int.TryParse(cookieValue, CultureInfo.InvariantCulture, out size)) 
    { 
     return size; 
    } 
    // Couldn't parse... 
    return null; 
} 

をコメントで述べたように、あなたが書くことができる:あなたが使用することができ、

あなたはしようとしている場合は、StoriesPageSizeクッキーを使用するようにをしようとしますが、それは存在だかどうかわかりませんこれは、より一般的に利用できるようにする拡張メソッド:私は、インバリアントカルチャを使用するコードを変更した

public static int? GetInt32OrNull(this CookieCollection cookies, string name) 
{ 
    if (cookies == null) 
    { 
     throw ArgumentNullException("cookies"); 
    } 
    if (name == null) 
    { 
     throw ArgumentNullException("name"); 
    } 
    string cookieValue = cookies.Get(name).Value; 
    if (cookieValue == null) 
    { 
     return null; 
    } 
    int size; 
    if (int.TryParse(cookieValue, CultureInfo.InvariantCulture, out size)) 
    { 
     return size; 
    } 
    // Couldn't parse... 
    return null; 
} 

注 - それは不変の文化の中で、クッキーの情報を伝播することは理にかなって、それは本当にありませんとしてユーザーが目に見えるものや文化に敏感なものを意味します。 も、不変のカルチャを使用してクッキーを保存するようにしてください。とにかく

、(静的な非ジェネリックトップレベルのクラスで)代わりに拡張メソッドで、あなたが使用することができます。

size = size ?? Request.Cookies.GetInt32OrNull("StoriesPageSize") ?? 10; 
+0

あなたがしています投げ捨ててsizeFromCookie –

+0

@RuneFS:ほんとうに、ありがとう。実際には、簡単にインライン化することができます... –

+0

別の機能?それは結果としてNULL可能INTを可能ようconvert.ToInt32かのいずれかの過負荷があり – dpp

1

問題は、最初の操作(size ?? Convert.ToInt32(Request.Cookies.Get("StoriesPageSize").Value))の結果であるということですint。次に、このintと別のintとの間でNull Coalescing演算子を使用しますが、intをnullにすることはできないため、失敗します。

左側はnullにすることはできません場合はnull合体演算子を使用する意味を持っていないので、コンパイラはエラーを与えます。

それを修正する方法については、あなたはこのようにそれを書き換えることができます。

size = size ?? (Request.Cookies.Get("StoriesPageSize") != null ? Convert.ToInt32(Request.Cookies.Get("StoriesPageSize").Value) : 10); 
+0

Try /キャッチすると、FormatException、InvalidCastException、またはOverflowExceptionがスローされる可能性があります。 – rfmodulator