2015-06-26 3 views
19

non funziona:In C#, perché no?: L'operatore lavora con i gruppi lambda o metodo?

Func<string, byte[]> getFileContents = (Mode != null && Mode.ToUpper() == "TEXT") 
      ? TextFileContents 
      : BinaryFileContents; 

private static byte[] BinaryFileContents(string file) 
{ 
    return System.IO.File.ReadAllBytes(file); 
} 

private static byte[] TextFileContents(string file) 
{ 
    using (var sourceStream = new StreamReader(file)) 
    { 
     return Encoding.UTF8.GetBytes(sourceStream.ReadToEnd()); 
    } 
} 

errore è

nessuna conversione implicita tra il gruppo e il metodo di gruppo metodo

Works:

Func<string, byte[]> getFileContents2; 
if (Mode != null && Mode.ToUpper() == "TEXT") 
{ 
    getFileContents2 = TextFileContents; 
} 
else 
{ 
    getFileContents2 = BinaryFileContents; 
} 

Sono curioso di sapere perché? Mi sto perdendo qualcosa?

risposta

29

Le funzioni anonime e i gruppi di metodi non hanno tipi di per sé - sono semplicemente convertiti da a tipi di delegati (e tipi di albero di espressioni per alcune espressioni lambda).

Per l'operatore condizionale per determinare il tipo generale dell'espressione, almeno uno del secondo o terzo operando deve avere un tipo. Potresti trasmettere uno di loro a Func<string, byte[]> e il compilatore potrebbe scoprire che potrebbe convertire l'altro nello stesso tipo e essere felice.

Ad esempio:

Func<string, byte[]> getFileContents = DateTime.Now.Hour > 10 
    ? (Func<string, byte[]>) TextFileContents 
    : BinaryFileContents; 

Dalla sezione 7.14 del C# 5 spec:

Il secondo e terzo operandi, x ed y, da: comando del tipo del condizionale espressione.

  • Se x ha tipo X e Y ha tipo Y allora [...]
  • Se solo una di x ed y ha un tipo [...]
  • Altrimenti, nessun tipo di espressione può essere determinato e si verifica un errore in fase di compilazione.
+0

bello, e con la soluzione si può anche passare a var –

+1

Non ho capito veramente questa sfumatura," ... non hanno i tipi in se stessi - sono semplicemente convertibili * per * tipi delegato. ..", fino ad ora. Vale la pena più di +1. – William

+2

@billisphere: Sono contento di averlo aiutato :) Mi ci è voluto un * lungo * tempo per averlo anche io. (Lo stesso vale per il letterale 'null', btw. * La maggior parte * ha espressioni di tipi.) –