se le istruzioni corrispondono a più valori

Qual è il modo più semplice per scrivere questa affermazione?

if (value==1 || value==2)

Ad esempio … in SQL puoi dire where value in (1,2) invece di where value=1 or value=2 .

Sto cercando qualcosa che possa funzionare con qualsiasi tipo di base … string, int, ecc.

Che ne dite di:

 if (new[] {1, 2}.Contains(value)) 

È un trucco però 🙂

O se non ti dispiace creare il tuo metodo di estensione, puoi creare quanto segue:

 public static bool In(this T obj, params T[] args) { return args.Contains(obj); } 

E puoi usarlo in questo modo:

 if (1.In(1, 2)) 

🙂

Un modo più complicato 🙂 che emula il “IN” di SQL:

 public static class Ext { public static bool In(this T t,params T[] values){ foreach (T value in values) { if (t.Equals(value)) { return true; } } return false; } } if (value.In(1,2)) { // ... } 

Ma vai per il modo standard, è più leggibile.

EDIT : una soluzione migliore, secondo il suggerimento di @ Kobi:

 public static class Ext { public static bool In(this T t,params T[] values){ return values.Contains(t); } } 

E ‘questo quello che stai cercando ?

 if (new int[] { 1, 2, 3, 4, 5 }.Contains(value)) 

Se si dispone di un elenco, è ansible utilizzare .Contains (yourObject), se si sta solo cercando esistente (come un dove). Altrimenti guarda il metodo di estensione Linq. Any ().

Utilizzando Linq,

if(new int[] {1, 2}.Contains(value))

Ma dovrei pensare che il tuo originale sia più veloce.

In alternativa, e questo ti darebbe maggiore flessibilità se si testano valori diversi da 1 o 2 in futuro, è necessario utilizzare un’istruzione switch

 switch(value) { case 1: case 2: return true; default: return false } 

Se si cerca un valore in un elenco di valori fisso molte volte in un lungo elenco, deve essere utilizzato HashSet . Se l’elenco è molto breve (< ~ 20 voci), l'elenco potrebbe avere prestazioni migliori, in base a questo test HashSet rispetto alle prestazioni dell'elenco

 HashSet nums = new HashSet { 1, 2, 3, 4, 5 }; // .... if (nums.Contains(value)) 

Generalmente, no.

Sì, ci sono casi in cui l’elenco si trova in una Array o in un List , ma non è il caso generale.

Più facile è soggettivo, ma forse l’affermazione dell’interruttore sarebbe più semplice? Non è necessario ripetere la variabile, in modo che più valori possano adattarsi alla linea e una riga con molti confronti è più leggibile della controparte che utilizza l’istruzione if.

Un metodo di estensione come questo lo farebbe …

 public static bool In(this T item, params T[] items) { return items.Contains(item); } 

Usalo in questo modo:

 Console.WriteLine(1.In(1,2,3)); Console.WriteLine("a".In("a", "b")); 

In vb.net o C # mi aspetterei che l’approccio generale più veloce per confrontare una variabile con qualsiasi numero ragionevole di oggetti con nome separato (al contrario di tutte le cose di una collezione) sarà semplicemente confrontare ogni object con il confronto e molto come hai fatto È certamente ansible creare un’istanza di una raccolta e vedere se contiene l’object, e farlo potrebbe essere più espressivo che comparare l’object con tutti gli oggetti individualmente, ma a meno che non si usi un costrutto che il compilatore può riconoscere esplicitamente, tale codice quasi certamente sarà molto più lento del semplice fare i confronti individuali. Non mi preoccuperei della velocità se il codice per sua natura funzionasse al massimo alcune centinaia di volte al secondo, ma sarei diffidare dal fatto che il codice venga riproposto a qualcosa che viene eseguito molto più spesso di quanto inizialmente previsto.

Un approccio alternativo, se una variabile è qualcosa come un tipo di enumerazione, consiste nel scegliere valori di enumerazione power-of-two per consentire l’uso di maschere di bit. Se il tipo di enumerazione ha 32 o meno valori validi (ad esempio, iniziando Harry = 1, Ron = 2, Hermione = 4, Ginny = 8, Neville = 16) uno potrebbe memorizzarli in un numero intero e controllare più bit contemporaneamente in un singolo operation ((if ((thisOne & (Harry | Ron | Neville | Beatrix))! = 0) / * Fai qualcosa * /. Ciò consentirà un codice veloce, ma è limitato alle enumerazioni con un numero limitato di valori.

Un approccio un po ‘più potente, ma che deve essere usato con caucanvas, consiste nell’usare alcuni bit del valore per indicare gli attributi di qualcosa, mentre altri bit identificano l’elemento. Ad esempio, il bit 30 potrebbe indicare che un personaggio è maschile, il bit 29 potrebbe indicare un amico di Harry, ecc. Mentre i bit più bassi distinguono tra i caratteri. Questo approccio consentirebbe di aggiungere personaggi che potrebbero o meno essere amici di Harry, senza richiedere il codice che controlla la modifica di friend-of-Harry. Un avvertimento è che bisogna fare una distinzione tra le costanti di enumerazione utilizzate per impostare un valore di enumerazione e quelle utilizzate per testarlo. Ad esempio, per impostare una variabile per indicare Harry, si potrebbe desiderare di impostarla su 0x60000001, ma per vedere se una variabile è Harry, si dovrebbe testare il bit con 0x00000001.

Un altro approccio, che può essere utile se il numero totale di valori possibili è moderato (ad esempio 16-16.000 o giù di lì) è quello di avere una matrice di flag associata a ciascun valore. Si potrebbe quindi codificare qualcosa come “if (((characterAttributes [theCharacter] & chracterAttribute.Male)! = 0)”. Questo approccio funzionerà al meglio quando il numero di caratteri è piuttosto ridotto Se l’array è troppo grande, i messaggi di errore della cache potrebbero rallentare giù il codice al punto che testare contro un piccolo numero di caratteri individualmente sarebbe più veloce.

Utilizzo dei metodi di estensione:

 public static class ObjectExtension { public static bool In(this object obj, params object[] objects) { if (objects == null || obj == null) return false; object found = objects.FirstOrDefault(o => o.GetType().Equals(obj.GetType()) && o.Equals(obj)); return (found != null); } } 

Ora puoi fare questo:

 string role= "Admin"; if (role.In("Admin", "Director")) { ... } 
 public static bool EqualsAny(IEquatable value, params T[] possibleMatches) { foreach (T t in possibleMatches) { if (value.Equals(t)) return true; } return false; } public static bool EqualsAny(IEquatable value, IEnumerable possibleMatches) { foreach (T t in possibleMatches) { if (value.Equals(t)) return true; } return false; } 

Ho avuto lo stesso problema, ma l’ho risolto con un interruttore di istruzione switch (un valore che si sta triggersndo) {caso 1: il codice che si desidera verificare; caso 2: il codice che vuoi che accada; default: restituisce un valore}