Comment joindre int à une chaîne de caractères séparée dans .NET?

J’ai un tableau d’entiers:

int[] number = new int[] { 2,3,6,7 }; 

Quelle est la manière la plus simple de les convertir en une seule chaîne où les nombres sont séparés par un caractère (comme: "2,3,6,7" )?

Je suis en C # et .NET 3.5.

 var ints = new int[] {1, 2, 3, 4, 5}; var result = ssortingng.Join(",", ints.Select(x => x.ToSsortingng()).ToArray()); Console.WriteLine(result); // prints "1,2,3,4,5" 

EDIT :

Je vois que plusieurs solutions annoncent l’utilisation de SsortingngBuilder. Quelqu’un que la méthode Join doit prendre un argument IEnumerable.

Je vais vous décevoir 🙂 Ssortingng.Join nécessite un tableau pour une seule raison – la performance. La méthode de jointure doit connaître la taille des données pour pré-allouer efficacement la quantité de mémoire nécessaire.

Voici une partie de l’implémentation interne de la méthode Ssortingng.Join:

 // length computed from length of items in input array and length of separator ssortingng str = FastAllocateSsortingng(length); fixed (char* chRef = &str.m_firstChar) // note than we use direct memory access here { UnSafeCharBuffer buffer = new UnSafeCharBuffer(chRef, length); buffer.AppendSsortingng(value[startIndex]); for (int j = startIndex + 1; j <= num2; j++) { buffer.AppendString(separator); buffer.AppendString(value[j]); } } 

Je suis trop paresseux pour comparer les performances des méthodes suggérées. Mais quelque chose me dit que Join va gagner 🙂

Bien que l’OP ait spécifié .NET 3.5, les personnes souhaitant le faire dans .NET 2.0 avec C # 2 peuvent le faire:

 ssortingng.Join(",", Array.ConvertAll(ints, Convert.ToSsortingng)); 

Je trouve qu’il existe un certain nombre d’autres cas où l’utilisation des fonctions Convert.xxx est une alternative plus simple à un lambda, bien que dans C # 3, le lambda puisse aider l’inférence de type.

Voici une version assez compacte de C # 3 qui fonctionne avec .NET 2.0:

 ssortingng.Join(",", Array.ConvertAll(ints, item => item.ToSsortingng())) 

Un mélange des deux approches consisterait à écrire une méthode d’extension sur IEnumerable qui utilise un SsortingngBuilder. Voici un exemple, avec différentes surcharges selon que vous souhaitiez spécifier la transformation ou simplement vous fier à Plain ToSsortingng. J’ai nommé la méthode “JoinSsortingngs” au lieu de “Join” pour éviter toute confusion avec l’autre type de jointure. Peut-être que quelqu’un peut venir avec un meilleur nom 🙂

 using System; using System.Collections.Generic; using System.Text; public static class Extensions { public static ssortingng JoinSsortingngs(this IEnumerable source, Func projection, ssortingng separator) { SsortingngBuilder builder = new SsortingngBuilder(); bool first = true; foreach (T element in source) { if (first) { first = false; } else { builder.Append(separator); } builder.Append(projection(element)); } return builder.ToSsortingng(); } public static ssortingng JoinSsortingngs(this IEnumerable source, ssortingng separator) { return JoinSsortingngs(source, t => t.ToSsortingng(), separator); } } class Test { public static void Main() { int[] x = {1, 2, 3, 4, 5, 10, 11}; Console.WriteLine(x.JoinSsortingngs(";")); Console.WriteLine(x.JoinSsortingngs(i => i.ToSsortingng("X"), ",")); } } 
 Ssortingng.Join(";", number.Select(item => item.ToSsortingng()).ToArray()); 

Nous devons convertir chacun des éléments en une Ssortingng avant de pouvoir les joindre, il est donc logique d’utiliser Select et une expression lambda. Ceci est équivalent à map dans d’autres langues. Ensuite, nous devons convertir la collection de chaînes résultante en un tableau, car Ssortingng.Join accepte uniquement un tableau de chaînes.

Le ToArray() est un peu moche je pense. Ssortingng.Join devrait vraiment accepter IEnumerable , il n’y a aucune raison de le limiter aux tableaux uniquement. Ceci est probablement dû au fait que Join vient d’avant les génériques, lorsque les tableaux étaient le seul type de collection typé disponible.

Si votre tableau d’entiers peut être volumineux, vous obtiendrez de meilleures performances en utilisant un SsortingngBuilder. Par exemple:

 SsortingngBuilder builder = new SsortingngBuilder(); char separator = ','; foreach(int value in integerArray) { if (builder.Length > 0) builder.Append(separator); builder.Append(value); } ssortingng result = builder.ToSsortingng(); 

Edit: Lorsque j’ai posté ceci, j’ai eu l’impression à tort que “SsortingngBuilder.Append (int value)” était géré en interne pour append la représentation sous forme de chaîne de la valeur entière sans créer d’object ssortingng. C’est faux: l’inspection de la méthode avec Reflector montre qu’elle ajoute simplement value.ToSsortingng ().

Par conséquent, la seule différence de performance potentielle est que cette technique évite la création d’un tableau et libère les chaînes pour la récupération de place un peu plus tôt. En pratique, cela ne fera pas de différence mesurable. J’ai donc opté pour cette meilleure solution .

La question est de “la manière la plus simple de les convertir en une chaîne unique où le nombre est séparé par un caractère”.

Le plus simple est:

 int[] numbers = new int[] { 2,3,6,7 }; ssortingng number_ssortingng = ssortingng.Join(",", numbers); // do whatever you want with your exciting new number ssortingng 

EDIT: Cela ne fonctionne que dans .NET 4.0+, j’ai manqué le besoin de .NET 3.5 la première fois que j’ai lu la question.

Je suis d’accord avec l’expression lambda pour la lisibilité et la maintenabilité, mais ce ne sera pas toujours la meilleure option. L’inconvénient de l’utilisation des deux approches IEnumerable / ToArray et SsortingngBuilder est qu’elles doivent développer dynamicment une liste d’éléments ou de caractères, car elles ne savent pas combien d’espace sera nécessaire pour la chaîne finale.

Si le cas rare où la vitesse est plus importante que la concision, le suivant est plus efficace.

 int[] number = new int[] { 1, 2, 3, 4, 5 }; ssortingng[] ssortingngs = new ssortingng[number.Length]; for (int i = 0; i < number.Length; i++) strings[i] = number[i].ToString(); string result = string.Join(",", strings); 
 ints.Aggregate("", ( str, n ) => str +","+ n ).Subssortingng(1); 

Je pensais aussi qu’il y avait un moyen plus simple. Je ne sais pas sur la performance, quelqu’un a une idée (théorique)?

Dans .NET 4.0, la jointure de chaîne a une surcharge pour l’ params object[] , elle est donc aussi simple que:

 int[] ids = new int[] { 1, 2, 3 }; ssortingng.Join(",", ids); 

Exemple

 int[] ids = new int[] { 1, 2, 3 }; System.Data.Common.DbCommand cmd = new System.Data.SqlClient.SqlCommand("SELECT * FROM some_table WHERE id_column IN (@bla)"); cmd.CommandText = cmd.CommandText.Replace("@bla", ssortingng.Join(",", ids)); 

Dans .NET 2.0, c’est un peu plus difficile car il n’y a pas de surcharge. Donc, vous avez besoin de votre propre méthode générique:

 public static ssortingng JoinArray(ssortingng separator, T[] inputTypeArray) { ssortingng strRetValue = null; System.Collections.Generic.List ls = new System.Collections.Generic.List(); for (int i = 0; i < inputTypeArray.Length; ++i) { string str = System.Convert.ToString(inputTypeArray[i], System.Globalization.CultureInfo.InvariantCulture); if (!string.IsNullOrEmpty(str)) { // SQL-Escape // if (typeof(T) == typeof(string)) // str = str.Replace("'", "''"); ls.Add(str); } // End if (!string.IsNullOrEmpty(str)) } // Next i strRetValue= string.Join(separator, ls.ToArray()); ls.Clear(); ls = null; return strRetValue; } 

Dans .NET 3.5, vous pouvez utiliser des méthodes d'extension:

 public static class ArrayEx { public static ssortingng JoinArray(this T[] inputTypeArray, ssortingng separator) { ssortingng strRetValue = null; System.Collections.Generic.List ls = new System.Collections.Generic.List(); for (int i = 0; i < inputTypeArray.Length; ++i) { string str = System.Convert.ToString(inputTypeArray[i], System.Globalization.CultureInfo.InvariantCulture); if (!string.IsNullOrEmpty(str)) { // SQL-Escape // if (typeof(T) == typeof(string)) // str = str.Replace("'", "''"); ls.Add(str); } // End if (!string.IsNullOrEmpty(str)) } // Next i strRetValue= string.Join(separator, ls.ToArray()); ls.Clear(); ls = null; return strRetValue; } } 

Vous pouvez donc utiliser la méthode d'extension JoinArray.

 int[] ids = new int[] { 1, 2, 3 }; ssortingng strIdList = ids.JoinArray(","); 

Vous pouvez également utiliser cette méthode d'extension dans .NET 2.0 si vous ajoutez l'extension ExtensionAtsortingbute à votre code:

 // you need this once (only), and it must be in this namespace namespace System.Runtime.ComstackrServices { [AtsortingbuteUsage(AtsortingbuteTargets.Assembly | AtsortingbuteTargets.Class | AtsortingbuteTargets.Method)] public sealed class ExtensionAtsortingbute : Atsortingbute {} } 

Tu peux faire

 ints.ToSsortingng(",") ints.ToSsortingng("|") ints.ToSsortingng(":") 

Check-out

Séparateur Délimité ToSsortingng pour Array, List, Dictionary, IEnumerable générique