2012-06-15 11 views
15

पर ऑब्जेक्ट इकाई मैं सभी मूल्यों (गुणों) को सी # में सीएसवी फॉर्मेटेड स्ट्रिंग में कैसे लिख सकता हूं? जैसे:सीएसवी क्रमबद्धता/रूपांतरण

class Person(string firstName, string lastName, int_age); 
Person person = new Person("Kevin","Kline",33); 
अब

मैं एक स्ट्रिंग चाहते "केविन; क्लाइन, 33"

दूसरे शब्दों में मैं सीएसवी

में एक वस्तु को क्रमानुसार करना चाहते
+4

क्या मूल्य है? –

+0

बंद करने के लिए उम्मीदवार होने से बचने के लिए आपके प्रश्न को कहीं अधिक पृष्ठभूमि और डेटा/कोड के उदाहरणों की आवश्यकता है। –

+1

क्या आप हमें दिखा सकते हैं कि आपने पहले से क्या प्रयास किया है? – LolCat

उत्तर

2

आप कुछ इस तरह का उपयोग कर सकते हैं:

... 
     PropertyInfo[] properties = obj.GetType().GetProperties(); 
     string CSVRow = ""; 
     foreach (PropertyInfo pi in properties) 
     { 
      CSVRow = CSVRow + pi.GetValue(obj, null) + ";"; 
     } 
     CSVRow.Remove(CSVRow.Length - 1, 1); 
... 
+3

... लेकिन कोटिंग/एस्केपिंग नियमों को लागू करने की भी आवश्यकता होगी। – Joe

0

कुछ इस तरह:

public string ToCsv() 
{ 
    return string.Join(";", new string[]{ 
     _firstName, 
     _lastName, 
     _age.ToString() 
    }.Select(str=>Escape(str))); 
} 

या, प्रतिबिंब का उपयोग कर,

public static string ToCsv(this object obj) 
{ 
    return string.Join(";", 
     this.GetType().GetProperties().Select(pi=> 
      Escape(pi.GetValue(this, null).ToString()) 
     )); 
} 

कहाँ एस्केप एक उपयुक्त बचने कार्य है।

9

प्रतिबिंब का उपयोग कर आप एक वस्तु से संपत्ति infos प्राप्त कर सकते हैं

foreach (PropertyInfo prp in obj.GetType().GetProperties()) { 
    if (prp.CanRead) { 
     object value = prp.GetValue(obj, null); 
     string s = value == null ? "" : value.ToString(); 
     string name = prp.Name; 
     ... 
    } 
} 

GetProperties विधि एक अधिभार जिसके माध्यम से आप तय कर सकते हैं संपत्ति आप किस प्रकार की जरूरत है, जैसे निजी/सार्वजनिक दृष्टांत/स्थिर BindingFlags को स्वीकार किया है ।

आप उन्हें इस

var properties = type.GetProperties(BindingFlags.Public | 
            BindingFlags.NonPublic | 
            BindingFlags.Instance); 

आपकी समस्या पर लागू की तरह गठजोड़ कर सकते हैं आप

List<Person> people = ...; 
Type type = typeof(Person); 
PropertyInfo[] properties = type.GetProperties(); 
var sb = new StringBuilder(); 

// First line contains field names 
foreach (PropertyInfo prp in properties) { 
    if (prp.CanRead) { 
     sb.Append(prp.Name).Append(';'); 
    } 
} 
sb.Length--; // Remove last ";" 
sb.AppendLine(); 

foreach (Person person in people) { 
    foreach (PropertyInfo prp in properties) { 
     if (prp.CanRead) { 
      sb.Append(prp.GetValue(person, null)).Append(';'); 
     } 
    } 
    sb.Length--; // Remove last ";" 
    sb.AppendLine(); 
} 

File.AppendAllText("C:\Data\Persons.csv", sb.ToString()); 

लिख सकता है यह भी एक अच्छा विचार दोहरे उद्धरण में तार संलग्न करने के लिए है और डबल्स से बचने के लिए उद्धरण वे उन्हें दोगुना करके होते हैं।

Kevin;Kline;33 
13

var person = new Person("Kevin","Kline",33); 
using (var csv = new CsvWriter(new StreamWriter("file.csv"))) 
{ 
    csv.Configuration.HasHeaderRecord = false; 
    csv.Configuration.Delimiter = ';'; 
    csv.WriteRecord(person); 
} 

आउटपुट पर Josh Close's उत्कृष्ट CSVHelper पुस्तकालय एक नज़र आपके लिए एक संभावित कार्यान्वयन, जो जटिल वस्तुओं (गहरी वस्तु क्रमबद्धता) को पढ़ता है, जैसे गुणों के साथ वस्तुओं की सरणी ऑब्जेक्ट्स का एई, और सीएसवी फ़ाइल की तरह स्वरूपित एक स्ट्रिंग को बचाता है:

private string ToCsv(string separator, IEnumerable<object> objectList) 
{ 
    StringBuilder csvData = new StringBuilder(); 
    foreach (var obj in objectList) 
    { 
     csvData.AppendLine(ToCsvFields(separator, obj)); 
    } 
    return csvData.ToString(); 
} 

private string ToCsvFields(string separator, object obj) 
{ 
    var fields = obj.GetType().GetProperties(); 
    StringBuilder line = new StringBuilder(); 

    if (obj is string) 
    { 
     line.Append(obj as string); 
     return line.ToString(); 
    } 

    foreach (var field in fields) 
    { 
     var value = field.GetValue(obj); 
     var fieldType = field.GetValue(obj).GetType(); 

     if (line.Length > 0) 
     { 
      line.Append(separator); 
     } 
     if (value == null) 
     { 
      line.Append("NULL"); 
     } 
     if (value is string) 
     { 
      line.Append(value as string); 
     } 
     if (typeof(IEnumerable).IsAssignableFrom(fieldType)) 
     { 
      var objectList = value as IEnumerable; 
      StringBuilder row = new StringBuilder(); 

      foreach (var item in objectList) 
      { 
       if (row.Length > 0) 
       { 
        row.Append(separator); 
       } 
       row.Append(ToCsvFields(separator, item)); 
      } 
      line.Append(row.ToString()); 
     } 
     else 
     { 
      line.Append(value.ToString()); 
     } 
    } 
    return line.ToString(); 
} 
+0

क्या सीएसवीहेल्पर का उपयोग करना संभव है, बचत फ़ाइल.csv भाग के बिना? मैं एचडी में फ़ाइल नहीं लिखना चाहता, मैं वेब उपयोगकर्ता को प्रतिक्रिया के रूप में फ़ाइल भेजने का इरादा रखता हूं। – Lombas

+4

बेस्ट हिस्सा यह है कि यह नेट कोर –

2

मेरा मानना ​​है कि FileHelpers इस के लिए अच्छा है, मैं इसे गुस्से में अपने आप का उपयोग नहीं किया गया है, हालांकि

+0

के लिए उपलब्ध है यह अच्छा है। बहुत बुरा यह नेट कोर के लिए काम नहीं करता है हालांकि:/CSVHelper करता है !! –