2013-03-28 9 views
9

Come funziona l'operatore is rispetto al DLR?Come funziona l'operatore "è" con oggetti dinamici?

a fare la mia domanda un po 'più esplicito, si consideri la seguente firma:

public bool Is<T>(Func<dynamic> getInstance) 
{ 
    return getInstance() is T; 
} 

Per impostazione predefinita, quali sono le condizioni necessarie per Is<T> per tornare true? Inoltre, il DLR fornisce un meccanismo per personalizzare questo comportamento?

+0

Che tipo di comportamento di personalizzazione vorresti? –

+0

@ReedCopsey, ducktyping granulare: mi piacerebbe essere in grado di fare qualcosa come avere un'interfaccia: 'interfaccia pubblica INAMED {stringa Nome {get; }} 'e quando controllo' getInstance() è INamed' per fare in modo che l'implementazione personalizzata 'DynamicMetaObject' restituisca true se l'oggetto dinamico contiene una proprietà stringa chiamata" Name ". Eventuali suggerimenti? – smartcaveman

+0

Dovresti implementare i controlli tu stesso, probabilmente utilizzando la riflessione sull'interfaccia, ecc. –

risposta

6

In fase di esecuzione, dynamic viene considerato uguale a object, il che significa che il tipo di runtime del risultato del delegato getInstance verrà utilizzato per eseguire questo controllo. L'unica differenza che si ottiene utilizzando dynamic è che non verrà eseguito il controllo del tempo di compilazione e che il binding dinamico verrà utilizzato in fase di esecuzione per eseguire questo controllo sull'oggetto dinamico restituito da getInstance.

Per impostazione predefinita, quali condizioni sono necessarie per È per restituire true?

Il delegato inoltrato dovrà restituire un tipo che, in fase di runtime, è compatibile con T.

Inoltre, il DLR fornisce un meccanismo per personalizzare questo comportamento?

No. Verrà utilizzato le regole standard per i tipi C#. Qualsiasi comportamento personalizzato dovrebbe essere scritto nella logica stessa.

+0

Quindi, il risultato è lo stesso di 'typeof (T). GetType(). IsInstanceOfType (getInstance()) '? – smartcaveman

+0

@smartcaveman È più come usare [Type.IsAssignableFrom] (http://msdn.microsoft.com/en-us/library/system.type.isassignablefrom.aspx), ovvero: 'typeof (T) .IsAssignableFrom (getInstance () .GetType()) ' –

+0

In questo caso non ci sono differenze nell'uso di' oggetto'. – jbtule

0

Poiché is già è un test runtime, non c'è runtime supplementare vincolante svolto, infatti non ci sarà alcuna differenza IL compilato

public bool Is<T>(Func<object> getInstance) 
{ 
    return getInstance() is T; 
} 

La IL per il corpo del metodo di entrambi Is<T>(Func<object> getInstance) e Is<T>(Func<dynamic> getInstance):

.maxstack 2 
    .locals init (
     [0] bool CS$1$0000) 
    L_0000: nop 
    L_0001: ldarg.1 
    L_0002: callvirt instance !0 [mscorlib]System.Func`1<object>::Invoke() 
    L_0007: isinst !!T 
    L_000c: ldnull 
    L_000d: cgt.un 
    L_000f: stloc.0 
    L_0010: br.s L_0012 
    L_0012: ldloc.0 
    L_0013: ret 

Quindi la risposta è che is parola chiave non sia effettuata con l'utilizzo del DLR, funziona lo stesso come se si utilizza il tipo object.

+0

Quindi non c'è nessuna differenza compilata? E se fosse un'istanza di DynamicObject o qualcosa del genere? – usr

+0

Se si tratta di un oggetto DynamicObject, sarà true solo se bool è . E sì, puoi scrivere il codice, compilarlo e in entrambi i casi sarà lo stesso IL. – jbtule

+0

Non ne sono così sicuro. DynamicObject è trattato appositamente. Può essere usato per personalizzare molti comportamenti (si pensi a ExpandoObject). Ha anche una funzione TryConvert. Inoltre, cosa succede se l'oggetto è un oggetto python? Sono sicuro che le regole di Python per la conversione dei tipi sono diverse, quindi sono probabilmente personalizzabili ?! – usr

Problemi correlati