ASP.NET MVCのViewBagのしくみ


102

ASP.NET MVCはどのように機能しますViewBagか?MSDNによると、これは単なるでありObject、興味深いのはViewBag.Foo、マジックストリングなどの「マジック」プロパティがViewBag["Hello"]実際にどのように機能するかです。

また、どのように作成してASP.NET WebFormsアプリで使用できますか?

例をいただければ幸いです。


このページは既にコードビハインドファイル内の変数に直接アクセスしているため、この概念はWebFormsでは必要ないようです。MVCでは、ビューはViewBagまたはモデルで渡されるデータを除いて、コントローラー内の何にもアクセスできません。
Richard Dalton

回答:


91

ViewBagタイプですdynamicが、内部的にはSystem.Dynamic.ExpandoObject()

これは次のように宣言されています。

dynamic ViewBag = new System.Dynamic.ExpandoObject();

これがあなたができる理由です:

ViewBag.Foo = "Bar";

サンプルのExpanderオブジェクトコード:

public class ExpanderObject : DynamicObject, IDynamicMetaObjectProvider
{
    public Dictionary<string, object> objectDictionary;

    public ExpanderObject()
    {
        objectDictionary = new Dictionary<string, object>();
    }
    public override bool TryGetMember(GetMemberBinder binder, out object result)
    {
        object val;
        if (objectDictionary.TryGetValue(binder.Name, out val))
        {
            result = val;
            return true;
        }
        result = null;
        return false;
    }

    public override bool TrySetMember(SetMemberBinder binder, object value)
    {
        try
        {
            objectDictionary[binder.Name] = value;
            return true;
        }
        catch (Exception ex)
        {
            return false;
        }
    }
}

1
ViewBagのMSDNページに単にそれが言っpublic object ViewBag { get; }ているのは奇妙ですが、私はそれがであるExpandoObjectというあなたの主張を買っています。私のように、ここでのViewDataとの比較:「だから、基本的に[ViewBag]は...魔法特性を持つ[ViewDataをして]魔法の文字列を置き換えます」。; ^)
ruffin

public object ViewBag { get; }MSDN で言う@ruffinは奇妙なことに奇妙ですが、Codeはdynamic ViewBag { get .. 内部的にDynamicViewData
Aniket Inge

とてもいいです。掘り下げていただきありがとうございます。そして私は+1し、あなたを信じていると言いました!; ^)
ruffin

2
@ruffinドキュメントがあり、コードが決してない場合の別のケース
Aniket Inge

それほど明確ではない、または混合された質問に対して正しい答えを見つけると、ときどき感動します。ありがとう!
オスカーオルティス

33

これは動的オブジェクトです。つまり、コントローラでプロパティを追加し、後でビューでそれらを読み取ることができます。これは、基本的に動的型の機能であるオブジェクトを作成するのと同じであるためです。ダイナミクスに関するこのMSDNの記事を参照してください。MVCに関連した使用法については、この記事を参照してください 。

これをWebフォームに使用する場合は、次のように基本ページクラスに動的プロパティを追加します。

public class BasePage : Page
{

    public dynamic ViewBagProperty
    {
        get;
        set;
    }
}

すべてのページにこれを継承させます。ASP.NETマークアップで、次のことができるはずです。

<%= ViewBagProperty.X %>

うまくいくはずです。そうでない場合は、それを回避する方法があります。


ViewBagとは何か、WebFormsでそのようなオブジェクトを作成する方法を知りたいです。つまり、手動でコード化したいと考えています。
Aniket Inge 2013

上記の実装で更新されました。
ブライアンメインズ2013

8

ViewBagであるSystem.Dynamic.ExpandoObjectとして提案しました。のプロパティViewBagは基本的にKeyValueペアであり、キーによって値にアクセスします。この意味で、これらは同等です。

ViewBag.Foo = "Bar";
ViewBag["Foo"] = "Bar";

ViewBagとは何か、WebFormsでそのようなオブジェクトを作成する方法を知りたいです。つまり、手動でコード化したいと考えています。
Aniket Inge 2013

@Aniket WebフォームにViewStateがあります。
Konstantin Dinev 2013

5

ViewBagは、コントローラーアクションからビューにデータを渡して、渡されているデータをレンダリングするために使用されます。これで、ViewBagまたはViewDataを使用して、コントローラーアクションとビューの間でデータを渡すことができます。ViewBag:これは動的オブジェクトのタイプです。つまり、新しいフィールドをviewbagに動的に追加し、ビューでこれらのフィールドにアクセスできます。新しいフィールドを作成するときに、viewbagのオブジェクトを初期化する必要があります。

例:1. ViewBagの作成:ViewBag.FirstName = "John";

  1. ビューへのアクセス:@ ViewBag.FirstName。

3

ViewBagのタイプは動的です。もっと、あなたはできませんViewBag["Foo"]。例外が発生します-'System.Dynamic.DynamicObject'タイプの式に[]を使用したインデックス作成を適用できません

の内部実装はViewBagFooをViewData["Foo"](ViewDataDictionaryのタイプ)に実際に格納するため、これら2つは交換可能です。ViewData["Foo"]ViewBag.Foo

そしてスコープ。ViewBagとViewDataは、コントローラのアクションとレンダリングするビューの間でデータを受け渡すための機能です。


0

ViewBagは、動的に値を設定または取得できる動的な型であり、厳密に型指定されたクラスなしで任意の数の追加フィールドを追加できます。これにより、コントローラーからビューにデータを渡すことができます。コントローラで......

public ActionResult Index()
{
    ViewBag.victor = "My name is Victor";
    return View();
}

ビューで

@foreach(string a in ViewBag.victor)
{
     .........
}

私が学んだことは、どちらも動的な名前の保存プロパティ、つまりViewBag.victorを持つ必要があるということです。


-1
public dynamic ViewBag
{
    get
    {
        if (_viewBag == null)
        {
            _viewBag = new DynamicViewData(() => ViewData);
        }

        return _viewBag;
    }
}

3
共有したコードの前後にコンテキスト/コメントを追加してください。これは、質問者や他の将来の読者があなたの投稿をよりよく理解するのに役立ちます。
RBT
弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.