2011-05-21 11 views
20

LINQ a objetos compatible con las consultas sobre los objetos de cadena pero cuando se utiliza un código como a continuación:cómo `.Tomar()` en una cadena y obtener una cadena al final?

string SomeText = "this is some text in a string"; 
return SomeText.Take(6).ToString(); 

Todo lo que consigo es:

System.Linq.Enumerable+<TakeIterator>d__3a`1[System.Char] 

Esto se discute como un "accidente" en this question pero esto es lo que realmente estoy tratando de hacer y no puedo encontrarlo a través de la búsqueda en cualquier lugar.

Sé que hay otras maneras de manipular cadenas, pero también sé que puedes hacer algunos trucos realmente lindos con LINQ y solo me gustaría saber si hay una manera de recortar una cadena de cierta longitud con LINQ.

Respuesta

18

hay ningún método integrado en System.Linq para hacer esto, pero usted puede escribir su propio método de extensión con bastante facilidad:

public static class StringExtensions 
{ 
    public static string ToSystemString(this IEnumerable<char> source) 
    { 
     return new string(source.ToArray()); 
    } 
} 

Desafortunadamente, debido object.ToString existe en todos los objetos de .NET, que tendría que dé al método un nombre diferente para que el compilador invoque su método de extensión, no el ToString incorporado.

Según su comentario a continuación, es bueno cuestionar si este es el enfoque correcto. Debido String expone una gran cantidad de funcionalidad a través de sus métodos públicos, me gustaría poner en práctica este método como una extensión de String sí:

/// <summary> 
/// Truncates a string to a maximum length. 
/// </summary> 
/// <param name="value">The string to truncate.</param> 
/// <param name="length">The maximum length of the returned string.</param> 
/// <returns>The input string, truncated to <paramref name="length"/> characters.</returns> 
public static string Truncate(this string value, int length) 
{ 
    if (value == null) 
     throw new ArgumentNullException("value"); 
    return value.Length <= length ? value : value.Substring(0, length); 
} 

que usaría de la siguiente manera:

string SomeText = "this is some text in a string"; 
return SomeText.Truncate(6); 

Esto tiene la ventaja de no crear arreglos/objetos temporales cuando la cadena ya es más corta que la longitud deseada.

+0

Gracias. ¿Y esta es una forma "buena" de hacer las cosas? Es parte de un sistema más grande en el que paso un StringBuilder y '.Append()' ing una gran cantidad de datos para generar un archivo. Sé que no debería optimizar prematuramente, pero ¿está utilizando LINQ en la forma en que está sugiriendo desperdiciar mucha CPU/memoria cuando hay una forma más sencilla de hacerlo? En pocas palabras: ¿Usarías este código para recortar una cadena de cierta longitud en tu propio proyecto? – rtpHarry

+1

@rtpHarry Buena pregunta; Personalmente, no usaría LINQ para lograr esto, y habría actualizado mi respuesta con el enfoque que elegiría. –

+0

Gracias por sus comentarios adicionales, actualizaré mi código basado en esto :) – rtpHarry

15

Basta con crear cadena

string res = new string(SomeText.Take(6).ToArray()); 

también prestar atención a la cadena de métodos nativos

string res = SomeText.Substring(0, 6); 
+1

La subcadena se lanzará si 'SomeText' tiene menos de seis caracteres; Supuse que el OP quería un método que se comportara como 'Take' (es decir,, devuelve como máximo tantos caracteres, pero menos (sin excepción) si la cadena de entrada es más corta). –

3

SomeText.Take(6) voluntad devuelve un IEnumerable de carbón de carbón, y ToString método no devolverá el presunto cadena que necesita llámalo como el siguiente:

string [] array = SomeText.Take(6).ToArray(); 
string result = new string(array); 
6

Me he encontrado con esto algunas veces y uso lo siguiente:

string.Join(string.Empty,yourString.Take(5)); 
Cuestiones relacionadas