Konvertieren Sie alle Anfangsbuchstaben in Großbuchstaben und ruhen Sie für jedes Wort in Kleinbuchstaben

110

Ich habe eine Textfolge (meistens ca. 5-6 Wörter), die ich konvertieren muss.

Derzeit sieht der Text so aus:

THIS IS MY TEXT RIGHT NOW

Ich möchte es konvertieren in:

This Is My Text Right Now

Ich kann meine Sammlung von Zeichenfolgen durchlaufen, bin mir aber nicht sicher, wie ich diese Textänderung durchführen soll.

mrblah
quelle

Antworten:

251
string s = "THIS IS MY TEXT RIGHT NOW";

s = System.Threading.Thread.CurrentThread.CurrentCulture.TextInfo.ToTitleCase(s.ToLower());
jspcal
quelle
31
Haha, wirklich? Dort ist es? Ich liebe .NET, aber einige der API-Designer sind echte Idioten.
George Mauer
7
Beachten Sie, dass diese Methode zwar das tut, was der Fragesteller gefragt hat, aber ein naiver Algorithmus ist, der jedes Wort groß schreibt, unabhängig davon, um welche Art von Wort es sich handelt. Es ist nicht wirklich "Titelfall", da sich die Regeln für das Titelgehäuse in verschiedenen Sprachen unterscheiden. Es ist nicht einmal richtig für Englisch. Zum Beispiel sollte der Titel "Über einen Jungen" auf Englisch "Über einen Jungen" lauten, aber diese Methode würde "Über einen Jungen" ergeben. Wenn Sie einen echten Titel wünschen , müssen Sie Ihre eigene Methode schreiben.
Ryan Lundy
18
Ich würde sie nicht Idioten nennen. Die Sache mit "ToTitleCase" ist, dass es kulturabhängig ist, daher muss es sich im System.Globalization-Namespace befinden. Das Durchlaufen von CurrentThread erfolgt nur, um die aktuelle Kultur des Threads abzurufen (Beachten Sie, dass dies zu einem anderen Verhalten führen kann, wenn der Benutzer ein anderes Gebietsschema hat!). Sie können auch "CultureInfo.InvariantCulture.TextInfo.ToTitleCase ()" ausführen. Dies ist möglicherweise besser, da sich InvariantCulture in allen Kulturen gleich verhält. Aus Interesse George: Wo würden Sie eine kulturspezifische String-Funktion platzieren?
Michael Stum
3
Beachten Sie auch die Kommentare zu ALL UPPERCASE-Zeichenfolgen: msdn.microsoft.com/en-us/library/…
Michael Stum
2
Die Methode toLower () sollte ToLower () sein. Der erste Buchstabe der Methode beginnt mit Großbuchstaben
Alex
84

Ich ziehe es wahrscheinlich vor, ToTitleCase von CultureInfo ( System.Globalization ) aus aufzurufen als Thread.CurrentThread ( System.Threading )

string s = "THIS IS MY TEXT RIGHT NOW";
s = CultureInfo.CurrentCulture.TextInfo.ToTitleCase(s.ToLower());

aber es sollte das gleiche sein wie jspcal Lösung

BEARBEITEN

Eigentlich sind diese Lösungen nicht die gleichen : CurrentThread--calls -> CultureInfo!


System.Threading.Thread.CurrentThread.CurrentCulture

string s = "THIS IS MY TEXT RIGHT NOW";
s = System.Threading.Thread.CurrentThread.CurrentCulture.TextInfo.ToTitleCase(s.ToLower());

IL_0000:  ldstr       "THIS IS MY TEXT RIGHT NOW"
IL_0005:  stloc.0     // s
IL_0006:  call        System.Threading.Thread.get_CurrentThread
IL_000B:  callvirt    System.Threading.Thread.get_CurrentCulture
IL_0010:  callvirt    System.Globalization.CultureInfo.get_TextInfo
IL_0015:  ldloc.0     // s
IL_0016:  callvirt    System.String.ToLower
IL_001B:  callvirt    System.Globalization.TextInfo.ToTitleCase
IL_0020:  stloc.0     // s

System.Globalization.CultureInfo.CurrentCulture

string s = "THIS IS MY TEXT RIGHT NOW";
s = System.Globalization.CultureInfo.CurrentCulture.TextInfo.ToTitleCase(s.ToLower());

IL_0000:  ldstr       "THIS IS MY TEXT RIGHT NOW"
IL_0005:  stloc.0     // s
IL_0006:  call        System.Globalization.CultureInfo.get_CurrentCulture
IL_000B:  callvirt    System.Globalization.CultureInfo.get_TextInfo
IL_0010:  ldloc.0     // s
IL_0011:  callvirt    System.String.ToLower
IL_0016:  callvirt    System.Globalization.TextInfo.ToTitleCase
IL_001B:  stloc.0     // s

Verweise:

Filippo Vitale
quelle
16

Es gibt verschiedene Möglichkeiten, das erste Zeichen eines Strings in Großbuchstaben umzuwandeln.

Die erste Möglichkeit besteht darin, eine Methode zu erstellen, die einfach das erste Zeichen begrenzt und den Rest der Zeichenfolge mithilfe eines Teilstrings anfügt:

public string UppercaseFirst(string s)
    {
        return char.ToUpper(s[0]) + s.Substring(1);
    }

Die zweite Möglichkeit (die etwas schneller ist) besteht darin, die Zeichenfolge in ein char-Array aufzuteilen und die Zeichenfolge dann neu zu erstellen:

public string UppercaseFirst(string s)
    {
        char[] a = s.ToCharArray();
        a[0] = char.ToUpper(a[0]);
        return new string(a);
    }
Jamie Dixon
quelle
1
Diese Lösung beantwortet die Frage nicht genau. Der Titel der Frage lautet "Konvertiere alle Anfangsbuchstaben in Großbuchstaben, ruhe für jedes Wort in Kleinbuchstaben". Bei dieser Lösung wird jedoch nur der erste Buchstabe der gesamten Zeichenfolge großgeschrieben. Daher würde diese Lösung "Hallo Welt" in "Hallo Welt" anstatt in "Hallo Welt" konvertieren.
Brsfan
9

Ungetestet, aber so etwas sollte funktionieren:

var phrase = "THIS IS MY TEXT RIGHT NOW";
var rx = new System.Text.RegularExpressions.Regex(@"(?<=\w)\w");
var newString = rx.Replace(phrase,new MatchEvaluator(m=>m.Value.ToLowerInvariant()));

Im Wesentlichen heißt es: "Führen Sie eine Regex-Übereinstimmung für alle Vorkommen eines alphanumerischen Zeichens durch, das auf ein anderes alphanumerisches Zeichen folgt, und ersetzen Sie es dann durch eine Kleinbuchstabenversion von sich selbst."

George Mauer
quelle
In diesem Fall beginnen alle Großbuchstaben mit Großbuchstaben und werden mit Kleinbuchstaben fortgesetzt. Genau das, wonach ich gesucht habe.
M. Azyoksul
9

Wenn Sie auf einer Webseite verwenden, können Sie auch CSS verwenden:

style="text-transform:capitalize;"

M.Eren Çelik
quelle
2
Warum CSS? Wenn die Frage nach c # asp.net Regex fragt
Jay
1
Das Tag ASP.NETzeigt an, dass das OP dies im WEB tut. Dies ist natürlich nicht die Antwort auf die Frage, da OP die Lösung benötigt, C#aber es löst das Problem und kann eine alternative Lösung sein. +1
Muhammad Saqib
6

Beim Erstellen großer Tische ist Geschwindigkeit ein Problem, daher ist Jamie Dixons zweite Funktion am besten, aber sie funktioniert nicht vollständig wie sie ist ...

Es werden nicht alle Buchstaben in Kleinbuchstaben geschrieben, und es wird nur der erste Buchstabe der Zeichenfolge großgeschrieben, nicht der erste Buchstabe jedes Wortes in der Zeichenfolge. Die folgende Option behebt beide Probleme:

    public string UppercaseFirstEach(string s)
    {
        char[] a = s.ToLower().ToCharArray();

        for (int i = 0; i < a.Count(); i++ )
        {
            a[i] = i == 0 || a[i-1] == ' ' ? char.ToUpper(a[i]) : a[i];

        }

        return new string(a);
    }

Obwohl zu diesem Zeitpunkt ungewiss ist, ob dies immer noch die schnellste Option ist, könnte die Regexvon George Mauer bereitgestellte Lösung schneller sein ... jemand, der sich genug darum kümmert, sollte sie testen.

Serj Sagan
quelle
2
es funktioniert, aber ich habe dieses "a.Count ()" in a.Length
Christian
2

Ich weiß nicht, ob die unten stehende Lösung mehr oder weniger effizient ist als die Antwort von jspcal, aber ich bin mir ziemlich sicher, dass sie weniger Objekterstellung erfordert als die von Jamie und George.

string s = "THIS IS MY TEXT RIGHT NOW";
StringBuilder sb = new StringBuilder(s.Length);
bool capitalize = true;
foreach (char c in s) {
    sb.Append(capitalize ? Char.ToUpper(c) : Char.ToLower(c));
    capitalize = !Char.IsLetter(c);
}
return sb.ToString();
kurzlebig
quelle
1
Wenn wir uns mit der Objekterstellung befassen, warum nicht direkt mit einer for-Schleifenindizierung über s, anstatt einen StringBuilder zu verwenden?
Jball
0

Denken Sie zusätzlich zur ersten Antwort daran, den Startindex für die Zeichenfolgenauswahl an das Ende des Wortes zu ändern. Andernfalls wird die Reihenfolge der Buchstaben in der Zeichenfolge in umgekehrter Reihenfolge angezeigt.

s.SelectionStart=s.Length;
zia khan
quelle
0

Versuchen Sie diese Technik; Es gibt das gewünschte Ergebnis zurück

CultureInfo.CurrentCulture.TextInfo.ToTitleCase(str.ToLower());

Und vergessen Sie nicht zu verwenden System.Globalization.

Beyondo
quelle
0

Eine der möglichen Lösungen, an denen Sie interessiert sein könnten. Durchlaufen einer Reihe von Zeichen von rechts nach links und umgekehrt in einer Schleife.

public static string WordsToCapitalLetter(string value)
    {
        if (string.IsNullOrWhiteSpace(value))
        {
            throw new ArgumentException("value");
        }

        int inputValueCharLength = value.Length;
        var valueAsCharArray = value.ToCharArray();

        int min = 0;
        int max = inputValueCharLength - 1;

        while (max > min)
        {
            char left = value[min];
            char previousLeft = (min == 0) ? left : value[min - 1];

            char right = value[max];
            char nextRight = (max == inputValueCharLength - 1) ? right : value[max - 1];

            if (char.IsLetter(left) && !char.IsUpper(left) && char.IsWhiteSpace(previousLeft))
            {
                valueAsCharArray[min] = char.ToUpper(left);
            }

            if (char.IsLetter(right) && !char.IsUpper(right) && char.IsWhiteSpace(nextRight))
            {
                valueAsCharArray[max] = char.ToUpper(right);
            }

            min++;
            max--;
        }

        return new string(valueAsCharArray);
    }
RShp
quelle
0

Die Antwort von jspcal als String-Erweiterung.

Program.cs

class Program
{
    static void Main(string[] args)
    {
        var myText = "MYTEXT";
        Console.WriteLine(myText.ToTitleCase()); //Mytext
    }
}

StringExtensions.cs

using System;
public static class StringExtensions
{

    public static string ToTitleCase(this string str)
    {
        if (str == null)
            return null;

        return System.Threading.Thread.CurrentThread.CurrentCulture.TextInfo.ToTitleCase(str.ToLower());
    }
}
Joel Wiklund
quelle