.NET Formatear una cadena con espacios fijos

199

¿El método .NET String.Format permite la colocación de una cadena en una posición fija dentro de una cadena de longitud fija?

"La cuerda va aquí"
"La cuerda va aquí"
"La cuerda va aquí"

¿Cómo se hace esto usando .NET?

Editar - He intentado Format / PadLeft / PadRight hasta la muerte. No funcionan. No se porque. Terminé escribiendo mi propia función para hacer esto.

Editar : cometí un error y usé dos puntos en lugar de una coma en el especificador de formato. Debería ser "{0,20}".

Gracias por todas las excelentes y correctas respuestas.

usuario72491
fuente
48
Nunca tuve una pregunta de formato de cadena que no pude responder yendo a esta página: blog.stevex.net/index.php/string-formatting-in-csharp
jcollum
@jcollum: Me encantaría votar tu respuesta, pero no puedo hacer comentarios
Dinah
PadLeft funciona para mí, comprueba que estás dejando el espacio en PadLeft (20, 'AQUÍ VA UN ESPACIO')
Maestro Jedi Spooky
¿Qué significa "dejar el espacio adentro"? Si quiere decir: ¿estoy "recortando" la cuerda, entonces no. Aún no funciona.
user72491

Respuestas:

473

Esto le dará exactamente las cadenas que solicitó:

string s = "String goes here";
string lineAlignedRight  = String.Format("{0,27}", s);
string lineAlignedCenter = String.Format("{0,-27}",
    String.Format("{0," + ((27 + s.Length) / 2).ToString() +  "}", s));
string lineAlignedLeft   = String.Format("{0,-27}", s);
Guffa
fuente
64
Esto debe marcarse como la respuesta correcta a la pregunta, pero parece que el OP ha dejado stackoverflow.
Oliver
9
Si busca el cheque verde versus los votos más altos, no sabe cómo SO;)
Dave Jellison
2
@DaveJellison Parece que alguien necesita escribir un complemento para solucionarlo, o SO debería convertirlo en una preferencia de usuario configurable.
Walter Stabosz
1
@WalterStabosz no podría estar más de acuerdo.
Dave Jellison el
2
¿Por qué se hace esto en ,lugar de :como en todos los demás casos de uso de formato?
LuckyLikey
65

El primero y el último, al menos, son posibles utilizando la siguiente sintaxis:

String.Format("{0,20}", "String goes here");
String.Format("{0,-20}", "String goes here");
Konrad Rudolph
fuente
49

A partir de Visual Studio 2015, también puede hacer esto con cadenas interpoladas (es un truco del compilador, por lo que no importa a qué versión del marco .net apunte).

string value = "String goes here";
string txt1 = $"{value,20}";
string txt2 = $"{value,-20}";
Sprotty
fuente
9
es una característica ac # 6.
LuckyLikey
¡He estado usando C # 6 durante años y no lo sabía! Upvoted :)
Avrohom Yisroel
17

Te han mostrado PadLefty PadRight. Esto completará lo que falta PadCenter.

public static class StringUtils
{
    public static string PadCenter(this string s, int width, char c)
    {
        if (s == null || width <= s.Length) return s;

        int padding = width - s.Length;
        return s.PadLeft(s.Length + padding / 2, c).PadRight(width, c);
    }
}

Nota personal: no olvide actualizar su propio CV: "¡Un día, incluso arreglé el código de Joel Coehoorn!" ;-D -Serge

Joel Coehoorn
fuente
Joel, buen fragmento: estoy tratando de usarlo y no se centra del todo como está. Parece que la línea de retorno debería ser algo así como (no tengo suficiente representante para editar ...): return s.PadLeft ((padding / 2) + s.Length, c) .PadRight (width, c);
shaunmartin
11

prueba esto:

"String goes here".PadLeft(20,' ');
"String goes here".PadRight(20,' ');

para el centro, obtenga la longitud de la cuerda y haga padleft y padright con los caracteres necesarios

int len = "String goes here".Length;
int whites = len /2;
"String goes here".PadRight(len + whites,' ').PadLeft(len + whites,' ');
Maestro Jedi Spooky
fuente
Parece que las llamadas a String.Format () son superfluas.
Joel Coehoorn el
Los métodos de relleno son buenos ya que las opciones de formato requieren que las longitudes sean constantes (es decir, String.Format("{0,-length}", something)no se compilarán.)
Roberto
6

Gracias por la discusión, este método también funciona (VB):

Public Function StringCentering(ByVal s As String, ByVal desiredLength As Integer) As String
    If s.Length >= desiredLength Then Return s
    Dim firstpad As Integer = (s.Length + desiredLength) / 2
    Return s.PadLeft(firstpad).PadRight(desiredLength)
End Function
  1. StringCentering () toma dos valores de entrada y devuelve una cadena con formato.
  2. Cuando la longitud de s es mayor o igual que la longitud deisred , la función devuelve la cadena original.
  3. Cuando la longitud de s es menor que la longitud deseada , se rellenará en ambos extremos.
  4. Debido a que el espacio entre caracteres es entero y no hay medio espacio, podemos tener una división desigual del espacio. En esta implementación, la división mayor va al extremo principal.
  5. La función requiere .NET Framework debido a PadLeft () y PadRight () .
  6. En la última línea de la función, el enlace es de izquierda a derecha, por lo que se aplica el primer pad seguido del pad de Longeng deseado .

Aquí está la versión de C #:

public string StringCentering(string s, int desiredLength)
{
    if (s.Length >= desiredLength) return s;
    int firstpad = (s.Length + desiredLength) / 2;
    return s.PadLeft(firstpad).PadRight(desiredLength);
}

Para facilitar la comprensión, se usa la variable entera firstpad . s.PadLeft (firstpad) aplica los (número correcto de) espacios en blanco iniciales. El PadRight más a la derecha (deseado) tiene una encuadernación más baja termina aplicando espacios en blanco al final.

chi
fuente
1
Bienvenido a SO, chi. Este es otro ejemplo de una GRAN primera publicación y respuesta. +1
Brian
Gracias Brian, la pregunta original en la parte superior de esta publicación es un excelente punto de partida. Me inspiran todas las publicaciones y respuestas anteriores a las mías.
chi
1

Aquí hay una versión de VB.NET que creé, inspirada en la respuesta de Joel Coehoorn, la edición de Oliver y el comentario de shaunmartin:

    <Extension()>
Public Function PadCenter(ByVal [string] As String, ByVal width As Integer, ByVal c As Char) As String

    If [string] Is Nothing Then [string] = String.Empty
    If (width <= [string].Length) Then Return [string]

    Dim padding = width - [string].Length
    Return [string].PadLeft([string].Length + (padding \ 2), c).PadRight(width, c)

End Function

<Extension()>
Public Function PadCenter(ByVal [string] As String, ByVal width As Integer) As String

    If [string] Is Nothing Then [string] = String.Empty
    If (width <= [string].Length) Then Return [string]

    Dim padding = width - [string].Length
    Return [string].PadLeft([string].Length + (padding \ 2)).PadRight(width)

End Function

Esto se configura como una extensión de cadena, dentro de un Módulo público (la forma en que hace Extensiones en VB.NET, un poco diferente a C #). Mi pequeño cambio es que trata una cadena nula como una cadena vacía, y rellena una cadena vacía con el valor de ancho (satisface mis necesidades particulares). Esperemos que esto se convierta fácilmente a C # para cualquier persona que lo necesite. Si hay una mejor manera de hacer referencia a las respuestas, ediciones y comentarios que mencioné anteriormente, que inspiraron mi publicación, hágamelo saber y lo haré. Soy relativamente nuevo en la publicación y no pude resolverlo. deja un comentario (puede que todavía no tenga suficiente representante).

Jeff
fuente
0

Publiqué un artículo de CodeProject que puede ser lo que quieres.

Ver: AC # way para ancho indirecto y formato de estilo.

Básicamente es un método, FormatEx, que actúa como String.Format, excepto que permite un modificador de alineación centrado.

FormatEx("{0,c10}", value);

Significa centrar el valor de varArgs [0] en un campo de 10 caracteres, inclinarse hacia la derecha si se requiere un espacio de relleno adicional.

FormatEx("{0,c-10}", value);

Significa centrar el valor de varArgs [0] en un campo de 10 caracteres, inclínese hacia la izquierda si se requiere un espacio de relleno adicional.

Editar: Internamente, es una combinación de Joel's PadCenter con algún análisis para reestructurar el formato y varArgs para una llamada a String.Format que hace lo que desea.

-Jesse

Jesse Chisholm
fuente
-1

parece que quieres algo como esto, que colocará tu cadena en un punto fijo en una cadena de longitud constante:

Dim totallength As Integer = 100
Dim leftbuffer as Integer = 5
Dim mystring As String = "string goes here"
Dim Formatted_String as String = mystring.PadLeft(leftbuffer + mystring.Length, "-") + String.Empty.PadRight(totallength - (mystring.Length + leftbuffer), "-")

tenga en cuenta que esto tendrá problemas si mystring.length + leftbuffer excede la longitud total

Atilio Jobson
fuente
-7
/// <summary>
/// Returns a string With count chars Left or Right value
/// </summary>
/// <param name="val"></param>
/// <param name="count"></param>
/// <param name="space"></param>
/// <param name="right"></param>
/// <returns></returns>
 public static string Formating(object val, int count, char space = ' ', bool right = false)
{
    var value = val.ToString();
    for (int i = 0; i < count - value.Length; i++) value = right ? value + space : space + value;
    return value;
}
Paulos02
fuente
3
No use este código: genera muchas asignaciones de cadenas innecesarias. Utilice los especificadores de formato incorporado y los métodos de relleno en su lugar.
Oskar Berggren
1
santo ... imagina usar esto dentro de un bucle :)
LuckyLikey