2010-11-05 3 views
12

Bunu nasıl yaptığını bulmadım. Ne bulduğum, bu satırın (http://blog.stevex.net/string-formatting-in-csharp/):C printf gibi C# biçimindeki dizelerde maksimum karakter sayısı tanımlanabilir mi?

Hatları ile ilgili daha fazla bilgi edinmek için, bir dizinin içinde bir hizalama yoktur. Hizalama, String.Format çağrısında yazdırılan herhangi bir argüman için çalışır. Numune sadece parametre yerine biçimini kullanarak uzunluk argümanları uygulanamıyor

String.Format(“->{1,10}<-”, “Hello”); // gives "->     Hello<-" (left padded to 10) 
String.Format(“->{1,-10}<-”, “Hello”); // gives "->Hello     <-" (right padded to 10) 
+0

? Görmek istediğiniz şeylerin örneklerini gönderebilir misiniz? – Oded

+0

C biçimindeki dizeleri C# biçimindeki dizelere dönüştürmeyi deniyorum. C içinde% -4.4s ve benzerlerini belirtebilirsiniz. –

+0

neden aşağı oy? Bu önemli bir soru! –

cevap

7

değil "doğal" C# dize biçimlendirme tarafından desteklenen, dize nesnenin String.ToString yöntemleri sadece dize kendisini dönmek gibidir. SomeObject IFormattable arabirimini uygulayan eğer

string.Format("{0:xxx}",someobject); 

çağırdığınızda

, aşırı yük ToString(string format,IFormatProvider formatProvider) yöntem format parametre olarak "xxx" ile, çağrılır.

Yani, en çok, bu, .NET dizesi biçimlendirmesinin tasarımında bir kusur değil, yalnızca dize sınıfındaki işlevsellik eksikliği.

Gerçekten buna ihtiyacınız varsa, önerilen geçici çözümlerden herhangi birini kullanabilir veya kendi sınıfınızda IFormattable arabirimini oluşturabilirsiniz.

+0

teşekkürler! Kesinlikle haklısın. Bir şeylerin yokluğu olan sicim sınıfı. ama xxx'i bir formatın bir örneği olarak mı kullandınız ya da gerçekten bir şey ifade ediyor mu (ör. 3 karakter)? –

+0

@matti, no xxx sadece bir örnekti. Aslında, ne anlama geldiği IFormattable arayüzünün uygulanması ile karar verilir. Neyse (C++ sevgilisi olarak bahseder), C++ ile c biçiminde biçimlendirme C# * ile yazılmış olana göre *, bu özelliğin eksik olduğu gerçeğinin bir kusurundan bahsetmek bana oldukça garip geliyor;) –

0

üretir?

String.Format ("-> {0} < -", toFormat.PadRight (10)); // -> Merhaba < -

Veya bunu yapmanıza izin vermek için kendi biçimlendiricinizi yazın.

+0

c yorum soru –

0

Neden dize uzunluğunu sınırlamak için Substr kullanmıyorsunuz? Ne istiyorsun

String s = "abcdefghijklmnopqrstuvwxyz"; 
String.Format("Character limited: {0}", s.Substr(0, 10)); 
+0

c yorum soru –

+0

Hatta Substr bile her dilden farklı bazı garip uygulama olduğu gerçeğini kaçırdı. Bu geçici çözümü olduğu gibi kullandım ve dize 10 karakterden kısa olduğunda başarısız oluyor ... –

0

Maksimum genişlik ayarlamak için kullanılan bir "L" biçim belirteci uygulayan özel bir biçimlendirici yazdım. Bu, bir veritabanı sütunu veya Dynamics CRM alanı için hedeflendiğinde, biçimlendirilmiş çıktımızın boyutunu kontrol etmemiz gerektiğinde kullanışlıdır.

public class StringFormatEx : IFormatProvider, ICustomFormatter 
{ 
    /// <summary> 
    /// ICustomFormatter member 
    /// </summary> 
    public string Format(string format, object argument, IFormatProvider formatProvider) 
    { 
     #region func-y town 
     Func<string, object, string> handleOtherFormats = (f, a) => 
     { 
      var result = String.Empty; 
      if (a is IFormattable) { result = ((IFormattable)a).ToString(f, CultureInfo.CurrentCulture); } 
      else if (a != null) { result = a.ToString(); } 
      return result; 
     }; 
     #endregion 

     //reality check. 
     if (format == null || argument == null) { return argument as string; } 

     //perform default formatting if arg is not a string. 
     if (argument.GetType() != typeof(string)) { return handleOtherFormats(format, argument); } 

     //get the format specifier. 
     var specifier = format.Substring(0, 1).ToUpper(CultureInfo.InvariantCulture); 

     //perform extended formatting based on format specifier. 
     switch(specifier) 
     { 
      case "L": 
       return LengthFormatter(format, argument); 
      default: 
       return handleOtherFormats(format, argument); 
     } 
    } 

    /// <summary> 
    /// IFormatProvider member 
    /// </summary> 
    public object GetFormat(Type formatType) 
    { 
     if (formatType == typeof(ICustomFormatter)) 
      return this; 
     else 
      return null; 
    } 

    /// <summary> 
    /// Custom length formatter. 
    /// </summary> 
    private string LengthFormatter(string format, object argument) 
    { 
     //specifier requires length number. 
     if (format.Length == 1) 
     { 
      throw new FormatException(String.Format("The format of '{0}' is invalid; length is in the form of Ln where n is the maximum length of the resultant string.", format)); 
     } 

     //get the length from the format string. 
     int length = int.MaxValue; 
     int.TryParse(format.Substring(1, format.Length - 1), out length); 

     //returned the argument with length applied. 
     return argument.ToString().Substring(0, length); 
    } 
} 

Kullanımı Bu String.format nasıl kullanılacağına ilişkin bir cevap, ama uzatma yöntemleri kullanarak bir dize kısaltılması başka yol değildir

var result = String.Format(
    new StringFormatEx(), 
    "{0:L4} {1:L7}", 
    "Stack", 
    "Overflow"); 

Assert.AreEqual("Stac Overflo", result); 
0

olduğunu. Bu şekilde string.format olmadan bile maksimum uzunluğu doğrudan dizeye eklemenizi sağlar.

public static class ExtensionMethods 
{ 
    /// <summary> 
    /// Shortens string to Max length 
    /// </summary> 
    /// <param name="input">String to shortent</param> 
    /// <returns>shortened string</returns> 
    public static string MaxLength(this string input, int length) 
    { 
     if (input == null) return null; 
     return input.Substring(0, Math.Min(length, input.Length)); 
    } 
} 

örnek kullanımı:

string Test = "1234567890"; 
string.Format("Shortened String = {0}", Test.MaxLength(5)); 
string.Format("Shortened String = {0}", Test.MaxLength(50)); 

Output: 
Shortened String = 12345 
Shortened String = 1234567890 
tam olarak başarmak için çalışıyoruz ne