Splitting CamelCase

Ceci est tout asp.net c #.

J’ai un enum

public enum ControlSelectionType { NotApplicable = 1, SingleSelectRadioButtons = 2, SingleSelectDropDownList = 3, MultiSelectCheckBox = 4, MultiSelectListBox = 5 } 

La valeur numérique de ceci est stockée dans ma firebase database. J’affiche cette valeur dans une grid de données.

  

L’ID ne signifie rien pour un utilisateur, j’ai donc changé la colonne liée en une colonne modèle avec les éléments suivants.

      

C’est beaucoup mieux … Cependant, ce serait génial s’il y avait une fonction simple que je pourrais placer autour de l’Enum pour la séparer par un boîtier Camel afin que les mots soient bien intégrés dans la grid de données.

Note: Je suis pleinement conscient qu’il existe de meilleures façons de faire tout cela. Cet écran est purement utilisé en interne et je veux juste un rapide hack en place pour l’afficher un peu mieux.

En effet, une regex / replace est la voie à suivre, comme décrit dans l’autre réponse, mais cela pourrait aussi vous être utile si vous vouliez aller dans une direction différente.

  using System.ComponentModel; using System.Reflection; 

  public static ssortingng GetDescription(System.Enum value) { FieldInfo fi = value.GetType().GetField(value.ToSsortingng()); DescriptionAtsortingbute[] atsortingbutes = (DescriptionAtsortingbute[])fi.GetCustomAtsortingbutes(typeof(DescriptionAtsortingbute), false); if (atsortingbutes.Length > 0) return atsortingbutes[0].Description; else return value.ToSsortingng(); } 

cela vous permettra de définir vos Enums comme

 public enum ControlSelectionType { [Description("Not Applicable")] NotApplicable = 1, [Description("Single Select Radio Buttons")] SingleSelectRadioButtons = 2, [Description("Completely Different Display Text")] SingleSelectDropDownList = 3, } 

Pris à partir de

http://www.codeguru.com/forum/archive/index.php/t-412868.html

J’ai utilisé:

  public static ssortingng SplitCamelCase(ssortingng input) { return System.Text.RegularExpressions.Regex.Replace(input, "([AZ])", " $1", System.Text.RegularExpressions.RegexOptions.Comstackd).Trim(); } 

Tiré de http://weblogs.asp.net/jgalloway/archive/2005/09/27/426087.aspx

Cette regex (^[az]+|[AZ]+(?![az])|[AZ][az]+) peut être utilisée pour extraire tous les mots du nom camelCase ou PascalCase. Il fonctionne également avec des abréviations n’importe où dans le nom.

  • MyHTTPServer contiendra exactement 3 correspondances: My , HTTP , Server
  • myNewXMLFile contiendra 4 correspondances: my , New , XML , File

Vous pouvez ensuite les joindre en une seule chaîne en utilisant ssortingng.Join .

 ssortingng name = "myNewUIControl"; ssortingng[] words = Regex.Matches(name, "(^[az]+|[AZ]+(?![az])|[AZ][az]+)") .OfType() .Select(m => m.Value) .ToArray(); ssortingng result = ssortingng.Join(" ", words); 

Si C # 3.0 est une option, vous pouvez utiliser le one-liner suivant pour faire le travail:

 Regex.Matches(YOUR_ENUM_VALUE_NAME, "[AZ][az]+").OfType().Select(match => match.Value).Aggregate((acc, b) => acc + " " + b).TrimStart(' '); 

La réponse de Tillito ne gère pas les chaînes contenant déjà des espaces ou des acronymes. Cela le corrige:

 public static ssortingng SplitCamelCase(ssortingng input) { return Regex.Replace(input, "(?<=[az])([AZ])", " $1", RegexOptions.Compiled); } 

Voici une méthode d’extension qui gère les nombres et les caractères majuscules de manière sereine, et permet également des acronymes spécifiques aux majuscules dans la chaîne finale:

 using System; using System.Collections.Generic; using System.Linq; using System.Text; using System.Globalization; using System.Text.RegularExpressions; using System.Web.Configuration; namespace System { ///  /// Extension methods for the ssortingng data type ///  public static class ConventionBasedFormattingExtensions { ///  /// Turn CamelCaseText into Camel Case Text. ///  ///  ///  /// Use AppSettings["SplitCamelCase_AllCapsWords"] to specify a comma-delimited list of words that should be ALL CAPS after split ///  /// wordWordIDWord1WordWORDWord32Word2 /// Word Word ID Word 1 Word WORD Word 32 Word 2 /// /// wordWordIDWord1WordWORDWord32WordID2ID /// Word Word ID Word 1 Word WORD Word 32 Word ID 2 ID /// /// WordWordIDWord1WordWORDWord32Word2Aa /// Word Word ID Word 1 Word WORD Word 32 Word 2 Aa /// /// wordWordIDWord1WordWORDWord32Word2A /// Word Word ID Word 1 Word WORD Word 32 Word 2 A ///  public static ssortingng SplitCamelCase(this ssortingng input) { if (input == null) return null; if (ssortingng.IsNullOrWhiteSpace(input)) return ""; var separated = input; separated = SplitCamelCaseRegex.Replace(separated, @" $1").Trim(); //Set ALL CAPS words if (_SplitCamelCase_AllCapsWords.Any()) foreach (var word in _SplitCamelCase_AllCapsWords) separated = SplitCamelCase_AllCapsWords_Regexes[word].Replace(separated, word.ToUpper()); //Capitalize first letter var firstChar = separated.First(); //NullOrWhiteSpace handled earlier if (char.IsLower(firstChar)) separated = char.ToUpper(firstChar) + separated.Subssortingng(1); return separated; } private static readonly Regex SplitCamelCaseRegex = new Regex(@" ( (?<=[az])[A-Z0-9] (?# lower-to-other boundaries ) | (?<=[0-9])[a-zA-Z] (?# number-to-other boundaries ) | (?<=[AZ])[0-9] (?# cap-to-number boundaries; handles a specific issue with the next condition ) | (?<=[AZ])[AZ](?=[az]) (?# handles longer strings of caps like ID or CMS by splitting off the last capital ) )" , RegexOptions.Compiled | RegexOptions.IgnorePatternWhitespace ); private static readonly string[] _SplitCamelCase_AllCapsWords = (WebConfigurationManager.AppSettings["SplitCamelCase_AllCapsWords"] ?? "") .Split(new[] { ',' }, StringSplitOptions.RemoveEmptyEntries) .Select(a => a.ToLowerInvariant().Trim()) .ToArray() ; private static Dictionary _SplitCamelCase_AllCapsWords_Regexes; private static Dictionary SplitCamelCase_AllCapsWords_Regexes { get { if (_SplitCamelCase_AllCapsWords_Regexes == null) { _SplitCamelCase_AllCapsWords_Regexes = new Dictionary(); foreach(var word in _SplitCamelCase_AllCapsWords) _SplitCamelCase_AllCapsWords_Regexes.Add(word, new Regex(@"\b" + word + @"\b", RegexOptions.Comstackd | RegexOptions.IgnoreCase)); } return _SplitCamelCase_AllCapsWords_Regexes; } } } } 
 public enum ControlSelectionType { NotApplicable = 1, SingleSelectRadioButtons = 2, SingleSelectDropDownList = 3, MultiSelectCheckBox = 4, MultiSelectListBox = 5 } public class NameValue { public ssortingng Name { get; set; } public object Value { get; set; } } public static List EnumToList(bool camelcase) { var array = (T[])(Enum.GetValues(typeof(T)).Cast()); var array2 = Enum.GetNames(typeof(T)).ToArray(); List lst = null; for (int i = 0; i < array.Length; i++) { if (lst == null) lst = new List(); ssortingng name = ""; if (camelcase) { name = array2[i].CamelCaseFriendly(); } else name = array2[i]; T value = array[i]; lst.Add(new NameValue { Name = name, Value = value }); } return lst; } public static ssortingng CamelCaseFriendly(this ssortingng pascalCaseSsortingng) { Regex r = new Regex("(?<=[az])(?[AZ])|(?<=.)(?[AZ])(?=[az])"); return r.Replace(pascalCaseSsortingng, " ${x}"); } //In your form protected void Button1_Click1(object sender, EventArgs e) { DropDownList1.DataSource = GeneralClass.EnumToList(true); ; DropDownList1.DataTextField = "Name"; DropDownList1.DataValueField = "Value"; DropDownList1.DataBind(); } 

La solution d’Eoin Campbell fonctionne bien, sauf si vous avez un service Web.

Vous devrez effectuer les opérations suivantes car l’atsortingbut de description n’est pas sérialisable.

 [DataContract] public enum ControlSelectionType { [EnumMember(Value = "Not Applicable")] NotApplicable = 1, [EnumMember(Value = "Single Select Radio Buttons")] SingleSelectRadioButtons = 2, [EnumMember(Value = "Completely Different Display Text")] SingleSelectDropDownList = 3, } public static ssortingng GetDescriptionFromEnumValue(Enum value) { EnumMemberAtsortingbute atsortingbute = value.GetType() .GetField(value.ToSsortingng()) .GetCustomAtsortingbutes(typeof(EnumMemberAtsortingbute), false) .SingleOrDefault() as EnumMemberAtsortingbute; return atsortingbute == null ? value.ToSsortingng() : atsortingbute.Value; } 

Vous pouvez utiliser les méthodes d’extension C #

  public static ssortingng SpacesFromCamel(this ssortingng value) { if (value.Length > 0) { var result = new List(); char[] array = value.ToCharArray(); foreach (var item in array) { if (char.IsUpper(item)) { result.Add(' '); } result.Add(item); } return new ssortingng(result.ToArray()); } return value; } 

Ensuite, vous pouvez l’utiliser comme

 var result = "TestSsortingng".SpacesFromCamel(); 

Le résultat sera

Chaîne de test

Utiliser LINQ:

 var chars = ControlSelectionType.NotApplicable.ToSsortingng().SelectMany((x, i) => i > 0 && char.IsUpper(x) ? new char[] { ' ', x } : new char[] { x }); Console.WriteLine(new ssortingng(chars.ToArray())); 

Et si vous n’aimez pas utiliser regex – essayez ceci:

 public static ssortingng SeperateByCamelCase(this ssortingng text, char splitChar = ' ') { var output = new SsortingngBuilder(); for (int i = 0; i < text.Length; i++) { var c = text[i]; //if not the first and the char is upper if (i > 0 && char.IsUpper(c)) { var wasLastLower = char.IsLower(text[i - 1]); if (i + 1 < text.Length) //is there a next { var isNextUpper = char.IsUpper(text[i + 1]); if (!isNextUpper) //if next is not upper (start of a word). { output.Append(splitChar); } else if (wasLastLower) //last was lower but i'm upper and my next is an upper (start of an achromin). 'abcdHTTP' 'abcd HTTP' { output.Append(splitChar); } } else { //last letter - if its upper and the last letter was lower 'abcd' to 'abcd A' if (wasLastLower) { output.Append(splitChar); } } } output.Append(c); } return output.ToString(); } 

Passé ces tests, il n'aime pas les chiffres mais je n'en avais pas besoin.

  [TestMethod()] public void ToCamelCaseTest() { var testData = new ssortingng[] { "AAACamel", "AAA", "SplitThisByCamel", "AnA", "doesnothing", "a", "A", "aasdasdAAA" }; var expectedData = new ssortingng[] { "AAA Camel", "AAA", "Split This By Camel", "An A", "doesnothing", "a", "A", "aasdasd AAA" }; for (int i = 0; i < testData.Length; i++) { var actual = testData[i].SeperateByCamelCase(); var expected = expectedData[i]; Assert.AreEqual(actual, expected); } } 

J’ai aussi une enum que j’ai dû séparer. Dans mon cas, cette méthode a résolu le problème-

 ssortingng SeparateCamelCase(ssortingng str) { for (int i = 1; i < str.Length; i++) { if (char.IsUpper(str[i])) { str = str.Insert(i, " "); i++; } } return str; }