web-dev-qa-db-fra.com

Quelle est la différence entre dynamic (C # 4) et var?

J'avais lu une tonne d'articles sur ce nouveau mot clé fourni avec C # v4, mais je ne pouvais pas faire la différence entre "dynamique" et "var".

Cet article m'a fait réfléchir, mais je ne vois toujours pas de différence.

Est-ce que vous pouvez utiliser "var" uniquement en tant que variable locale, mais dynamique à la fois locale et globale?

Pourriez-vous afficher du code sans mot clé dynamique, puis afficher le même code avec mot clé dynamique?

192
Ivan Prodanov

var est typé de manière statique - le compilateur et le runtime savoir le type - ils vous épargnent un peu de frappe ... les éléments suivants sont 100% identiques:

var s = "abc";
Console.WriteLine(s.Length);

et

string s = "abc";
Console.WriteLine(s.Length);

Tout ce qui s'est passé, c'est que le compilateur a découvert que s devait être une chaîne (de l'initialiseur). Dans les deux cas, il sait (dans l’IL) que s.Length _ signifie que (instance) string.Length propriété.

dynamic est une bête très différente; il ressemble beaucoup à object, mais avec une répartition dynamique:

dynamic s = "abc";
Console.WriteLine(s.Length);

Ici, s est saisi sous forme dynamique. Il ne sait pas à propos de string.Length, parce qu'il ne sait pas rien à propos de s au moment de la compilation. Par exemple, les éléments suivants compileraient (mais ne seraient pas exécutés) également:

dynamic s = "abc";
Console.WriteLine(s.FlibbleBananaSnowball);

Au moment de l'exécution (uniquement), il vérifiait la propriété FlibbleBananaSnowball - il ne parvient pas à la trouver et explose sous une pluie d'étincelles.

Avec dynamic, les propriétés/méthodes/opérateurs/etc sont résolus au moment de l'exécution, en fonction de l'objet réel. Très pratique pour parler à COM (qui peut avoir des propriétés d’exécution seulement), au DLR ou à d’autres systèmes dynamiques, comme javascript.

441
Marc Gravell

Les variables déclarées avec var sont implicitement mais typées de manière statique . Les variables déclarées avec dynamic sont typées dynamiquement. Cette fonctionnalité a été ajoutée au CLR afin de prendre en charge des langages dynamiques tels que Ruby et Python.

J'ajouterais que cela signifie que les déclarations dynamic sont résolues au moment de l'exécution, var les déclarations sont résolues au moment de la compilation.

57
HVS

Je vais expliquer la différence entre dynamique et var.

dynamic d1;
d1 = 1;
d1 = "http://mycodelogic.com";

Cela fonctionnera. Le compilateur peut recréer le type de variable dynamique.
commence par créer le type sous la forme entier, puis le compilateur recréera le type sous la forme chaîne
mais en cas de var

var v1;  // Compiler will throw error because we have to initialized at the time of declaration  
var v2 = 1; // Compiler will create v1 as **integer**
v2 = "Suneel Gupta"; // Compiler will throw error because, compiler will not recreate the type of variable 

Lors de l'utilisation du mot clé 'var', le type est décidé par le compilateur lors de la compilation, tandis que lors de l'utilisation du mot clé 'dynamique', le type est décidé par le moteur d'exécution.
Mot clé ‘var’, variable locale fortement typée pour laquelle le compilateur est capable de déterminer le type à partir de l’expression d’initialisation - très utile pour la programmation LINQ.
Le compilateur ne dispose d'aucune information sur le type dynamique de la variable. donc le compilateur ne montrera aucune intelligence.
Le compilateur dispose de toutes les informations sur la valeur stockée de var type, de sorte que le compilateur affiche une intelligence.
dynamique le type peut être passé comme argument de fonction et la fonction peut également renvoyer un type d'objet
Mais
var le type ne peut pas être passé comme argument de fonction et la fonction ne peut pas retourner le type d'objet. Ce type de variable peut fonctionner dans la portée où il a été défini.
39
Suneel Gupta

var implique que la vérification de type statique (liaison anticipée) est appliquée. dynamique implique que la vérification de type dynamique (liaison tardive) est appliquée. En termes de code, tenez compte des éléments suivants:

class Junk
{
    public void Hello()
    {
        Console.WriteLine("Hello");
    }
}

class Program
{
    static void Main(String[] args)
    {
        var a = new Junk();
        dynamic b = new Junk();

        a.Hello();

        b.Hello();
    }
}

Si vous compilez cela et inspectez les résultats avec ILSpy, vous constaterez que le compilateur a ajouté un code de liaison tardif qui gérera l'appel à Hello () depuis b, alors que la liaison anticipée a été appliquée à a, il est possible d'appeler Hello. () directement.

par exemple. (Démontage ILSpy)

using System;
namespace ConsoleApplication1
{
    internal class Junk
    {
        public void Hello()
        {
            Console.WriteLine("Hello");
        }
    }
}

using Microsoft.CSharp.RuntimeBinder;
using System;
using System.Runtime.CompilerServices;
namespace ConsoleApplication1
{
    internal class Program
    {
        [CompilerGenerated]
        private static class <Main>o__SiteContainer0
        {
            public static CallSite<Action<CallSite, object>> <>p__Site1;
        }
        private static void Main(string[] args)
        {
            Junk a = new Junk();      //NOTE: Compiler converted var to Junk
            object b = new Junk();    //NOTE: Compiler converted dynamic to object
            a.Hello();  //Already Junk so just call the method.

                          //NOTE: Runtime binding (late binding) implementation added by compiler.
            if (Program.<Main>o__SiteContainer0.<>p__Site1 == null)
            {
                Program.<Main>o__SiteContainer0.<>p__Site1 = CallSite<Action<CallSite, object>>.Create(Binder.InvokeMember(CSharpBinderFlags.ResultDiscarded, "Hello", null, typeof(Program), new CSharpArgumentInfo[]
                {
                    CSharpArgumentInfo.Create(CSharpArgumentInfoFlags.None, null)
                }));
            }
            Program.<Main>o__SiteContainer0.<>p__Site1.Target(Program.<Main>o__SiteContainer0.<>p__Site1, b);
        }
    }
}

La meilleure chose à faire pour découvrir la différence est d'écrire vous-même une petite application pour console comme celle-ci et de la tester vous-même avec ILSpy.

14
series0ne

Une grande différence - vous pouvez avoir un type de retour dynamique.

dynamic Foo(int x)
{
    dynamic result;

    if (x < 5)
      result = x;
    else
      result = x.ToString();

    return result;
}
12
user2382351

Voici un exemple simple qui montre la différence entre Dynamic (4.0) et Var

dynamic  di = 20;
dynamic ds = "sadlfk";
var vi = 10;
var vsTemp= "sdklf";

Console.WriteLine(di.GetType().ToString());          //Prints System.Int32
Console.WriteLine(ds.GetType().ToString());          //Prints System.String
Console.WriteLine(vi.GetType().ToString());          //Prints System.Int32
Console.WriteLine(vsTemp.GetType().ToString());      //Prints System.String

**ds = 12;**   //ds is treated as string until this stmt now assigning integer.

Console.WriteLine(ds.GetType().ToString());          **//Prints System.Int32**

**vs = 12**; //*Gives compile time error* - Here is the difference between Var and Dynamic. var is compile time bound variable.

Shiva Mamidi

10
Shiva Mamidi

var n'est qu'un raccourci pour une déclaration de type normal, dans laquelle vous laissez le compilateur deviner le type correct.

dynamic est un nouveau type (statique), dans lequel toutes les vérifications sont effectuées au moment de l'exécution, et non par le compilateur.

7
gimel

Le type d'une variable déclarée avec var est déterminé par le compilateur, c'est un raccourci pour spécifier le nom du type, rien de plus.

Quelle que soit la dynamique choisie au moment de l'exécution, le compilateur n'a aucune idée du type réel et tous les accès aux méthodes/champs/propriétés associés à cette variable sont définis à l'exécution.

4
Richard

This est une belle vidéo youtube qui parle de var VS Dynamic avec une démonstration pratique.

Vous trouverez ci-dessous une explication plus détaillée avec instantané.

La variable est liée tôt (vérifiée statiquement) tandis que dynamique est liée tardivement (évaluée dynamiquement).

Le mot-clé Var examine vos données du côté droit puis, pendant la compilation, décide du type de données de votre main gauche. En d'autres termes, le mot-clé var vous enregistre simplement en tapant plein de choses. Regardez l'image ci-dessous où, lorsque nous avons donné des données de chaîne et que la variable x indique le type de données de chaîne dans l'info-bulle.

enter image description here

D'autre part, le mot clé dynamique est destiné à un but complètement différent. Les objets dynamiques sont évalués lors de l'exécution. Par exemple, dans le code ci-dessous, la propriété "Length" existe ou non. Elle est évaluée au moment de l'exécution. J'ai volontairement tapé un petit "l". s'appelait (PETIT "l").

enter image description here

3
Shivprasad Koirala
  1. Var et dynamique définissent le type.
  2. var au moment de la compilation et dynamique au moment de l'exécution.
  3. dans la déclaration var et l'initialisation sont obligatoires comme variable constante
  4. dans l'initialisation dynamique peut être au moment de l'exécution comme des variables en lecture seule.
  5. en type var quel que soit le type sont décidés au moment de l'initialisation ne peut pas changer ensuite
  6. dynamique peut adopter n'importe quel type, même l'utilisateur définit le type de données.
2
shhhhh

variable dynamique et variable var peuvent toutes les deux stocker n'importe quel type de valeur, mais il est nécessaire pour initialiser 'var' au moment de la déclaration.

Le compilateur ne dispose d'aucune information sur le type de variable 'dynamique'. var est sécurisé pour le compilateur. Le compilateur a toutes les informations sur la valeur stockée, de sorte qu'il ne cause aucun problème au moment de l'exécution.

Le type dynamique peut être passé comme argument de fonction et la fonction peut aussi le renvoyer. Le type var ne peut pas être passé comme argument de fonction et la fonction ne peut pas renvoyer le type d'objet. Ce type de variable peut fonctionner dans la portée où il a été défini.

En cas de diffusion dynamique, vous n'avez pas besoin de connaître la propriété et les méthodes associées au type stocké, alors que pour var Pas besoin de transtypage, le compilateur dispose de toutes les informations pour effectuer l'opération.

dynamique: utile lors du codage utilisant la réflexion ou le support de langage dynamique ou avec les objets COM, car nous avons besoin d'écrire moins de code.

var: Utile pour obtenir le résultat des requêtes linq. Dans le framework 3.5, il introduit la prise en charge de la fonctionnalité linq.

Référence: Counsellingbyabhi

2
Abhishek Gahlout
  1. Le mot clé Var (variable locale typée implicite) est utilisé pour définir les variables locales. Dans le cas de Var, le type de données sous-jacent est déterminé lors de la compilation elle-même en fonction de l'affectation initiale.Une fois l'affectation initiale effectuée avec le type Var, sera fortement typé. Si vous essayez de stocker une valeur incompatible avec le type Var, cela entraînera une erreur lors de la compilation.

Exemple:

Var strNameList=new List<string>(); By using this statement we can store list of names in the string format. 
strNameList.add("Senthil");
strNameList.add("Vignesh");

strNameList.add(45); // This statement will cause the compile time error.

Mais dans le type dynamique, le type sous-jacent n’est déterminé qu’au moment de l’exécution. Le type de données dynamique n’est pas vérifié au moment de la compilation et il n’est pas non plus fortement typé. Nous pouvons affecter une valeur initiale au type dynamique, puis le réaffecter à une nouvelle valeur au cours de sa vie.

Exemple:

dynamic test="Senthil";
Console.Writeline(test.GetType())  // System.String

test=1222;
Console.Writeline(test.GetType())  // System.Int32

test=new List<string>();
Console.Writeline(test.GetType())  //System.Collections.Generic.List'1[System.String]

Il ne fournit pas non plus de support IntelliSense. Il n'offre pas un meilleur support lorsque nous travaillons également avec linq.Parce qu'il ne prend pas en charge les expressions lambda, les méthodes d'extension et les méthodes anonymes.

1
kuttychutty

Voici les différences

  • var est typé de manière statique (temps de compilation), dynamique est typé de manière dynamique (temps d'exécution)

  • Une variable déclarée en tant que var ne peut être utilisée que localement, les variables dynamiques peuvent être transmises en tant que paramètres à la fonction (la signature de fonction peut définir un paramètre comme dynamique, mais pas var).

  • avec dynamic, la résolution des propriétés se produit au moment de l'exécution et ce n'est pas le cas avec var, ce qui signifie qu'au moment de la compilation, toute variable déclarée dynamique peut appeler une méthode qui peut ou non exister et que le compilateur ne génère pas d'erreur.

  • Le transtypage avec var n'est pas possible mais avec dynamique, c'est possible (vous pouvez transtyper un objet aussi dynamique que non var).

Arun Vijayraghavan

1
Arun Vijayraghavan

Ne confondez pas dynamique et var. La déclaration d'une variable locale à l'aide de var n'est qu'un raccourci syntaxique permettant au compilateur d'inférer le type de données spécifique à partir d'une expression. Le mot clé var ne peut être utilisé que pour déclarer des variables locales dans une méthode, tandis que le mot clé dynamique peut être utilisé pour les variables locales, les champs et les arguments. Vous ne pouvez pas convertir une expression en var, mais vous pouvez également transformer une expression en dynamique. Vous devez explicitement initialiser une variable déclarée à l'aide de var sans avoir à initialiser une variable déclarée avec dynamic.

1
Kartik M