J'ai un tampon de chaîne d'environ 2000 caractères et j'ai besoin de vérifier le tampon s'il contient une chaîne spécifique.
Fera la vérification dans une application Web ASP.NET 2.0 pour chaque webrequest.
Quelqu'un sait-il si la méthode String.Contains fonctionne mieux que la méthode String.IndexOf ?
// 2000 characters in s1, search token in s2
string s1 = "Many characters. The quick brown fox jumps over the lazy dog";
string s2 = "fox";
bool b;
b = s1.Contains(s2);
int i;
i = s1.IndexOf(s2);
Réponses:
Contains
appelsIndexOf
:Quels appels
CompareInfo.IndexOf
, qui utilise finalement une implémentation CLR.Si vous voulez voir comment les chaînes sont comparées dans le CLR, cela vous montrera (recherchez CaseInsensitiveCompHelper ).
IndexOf(string)
n'a pas d'options etContains()
utilise une comparaison ordinale (une comparaison octet par octet plutôt que d'essayer d'effectuer une comparaison intelligente, par exemple, e avec é).Ce
IndexOf
sera donc légèrement plus rapide (en théorie) car ilIndexOf
va directement à une recherche de chaîne en utilisant FindNLSString de kernel32.dll (la puissance du réflecteur!).Mis à jour pour .NET 4.0 - IndexOf n'utilise plus la comparaison ordinale et contient donc peut être plus rapide. Voir le commentaire ci-dessous.
la source
IndexOf()
utilise en effetStringComparison.CurrentCulture
etContains()
utiliseStringComparison.Ordinal
ce qui sera plus rapide. Mais en réalité, les différences de vitesse dont nous parlons sont infimes - le fait est que l'un appelle l'autre, et Contains est plus lisible si vous n'avez pas besoin de l'index. En d'autres termes, ne vous en faites pas.Cela n'aura probablement pas d'importance du tout. Lisez cet article sur Coding Horror;): http://www.codinghorror.com/blog/archives/001218.html
la source
Contains (s2) est plusieurs fois (sur mon ordinateur 10 fois) plus rapide que IndexOf (s2) car Contains utilise StringComparison.Ordinal qui est plus rapide que la recherche sensible à la culture que IndexOf effectue par défaut (mais cela peut changer dans .net 4.0 http: //davesbox.com/archive/2008/11/12/breaking-changes-to-the-string-class.aspx ).
Contains a exactement les mêmes performances que IndexOf (s2, StringComparison.Ordinal)> = 0 dans mes tests, mais il est plus court et rend votre intention claire.
la source
Je dirige un cas réel (à l'opposé d'un benchmark synthétique)
contre
C'est une partie vitale de mon système et elle est exécutée 131 953 fois (merci DotTrace).
Cependant choquant la surprise , le résultat est le contraire que prévu
: - /
net framework 4.0 (mis à jour au 13-02-2012)
la source
INT
c'est beaucoup plus grand queBOOL
, etIndexOf>=0
cause un pas de plusEn utilisant Reflector, vous pouvez voir que Contains est implémenté à l'aide d'IndexOf. Voici la mise en œuvre.
So Contains est probablement un peu plus lent que d'appeler IndexOf directement, mais je doute que cela ait une importance pour les performances réelles.
la source
Si vous voulez vraiment micro-optimiser votre code, votre meilleure approche est toujours l'analyse comparative.
Le framework .net a une excellente implémentation de chronomètre - System.Diagnostics.Stopwatch
la source
Après une petite lecture, il semble que sous le capot, la méthode String.Contains appelle simplement String.IndexOf. La différence est String.Contains renvoie un booléen tandis que String.IndexOf retourne un entier avec (-1) représentant que la sous-chaîne n'a pas été trouvée.
Je suggérerais d'écrire un petit test avec environ 100 000 itérations et de voir par vous-même. Si je devais deviner, je dirais qu'IndexOf est peut-être un peu plus rapide, mais comme je l'ai dit, il suffit de deviner.
Jeff Atwood a un bon article sur les chaînes sur son blog . Il s'agit davantage de concaténation, mais peut néanmoins être utile.
la source
Tout comme une mise à jour de cela, j'ai fait des tests et fourni que votre chaîne d'entrée est assez grande, alors le Regex parallèle est la méthode C # la plus rapide que j'ai trouvée (à condition que vous ayez plus d'un noyau, j'imagine)
Obtenir le nombre total de correspondances par exemple -
J'espère que cela t'aides!
la source
Utilisez une bibliothèque de référence, comme cette récente incursion de Jon Skeet pour la mesurer.
Caveat Emptor
Comme toutes les questions de (micro-) performances, cela dépend des versions du logiciel que vous utilisez, des détails des données inspectées et du code entourant l'appel.
Comme toutes les questions de (micro-) performances, la première étape doit être d'obtenir une version en cours d'exécution qui soit facilement maintenable. Ensuite, l'analyse comparative, le profilage et le réglage peuvent être appliqués aux goulots d'étranglement mesurés au lieu de deviner.
la source
Pour tous ceux qui lisent encore ceci, indexOf () fonctionnera probablement mieux sur la plupart des systèmes d'entreprise, car contains () n'est pas compatible avec IE!
la source