C#(将数据集转换为多个CSV字符串,保留类型并转换回)

时间:2019-03-13 21:31:52

标签: c# csv dataset

我刚遇到一个问题。我试图将数据集序列化为 json ,并使用 jose-jwt 对其进行加密。 但这不起作用,我不知道原因,但是在尝试检索时,数据为空白。

我需要的是一种将数据集转换为CSV列表并取回的方法,但保留列类型。

1 个答案:

答案 0 :(得分:0)

然后,我附带了我要共享的此代码,并询问是否有人有更简单的方法来进行共享。 (我毕竟是来这里学习的)

它具有一个为每个列添加一个额外列的选项,并且仅在标头中写入DataColumn.DataType。

using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Linq;
using System.Text;
using System.Threading;

namespace Demo
{
    public static class Utilities
    {
        private static char separator = '|';

        public static List<string> ToCSV(this DataSet ds, bool withTypes = false)
        {    
            List<string> lResult = new List<string>();

            foreach (DataTable dt in ds.Tables)
            {
                StringBuilder sb = new StringBuilder();
                IEnumerable<string> columnNames = dt.Columns.Cast<DataColumn>().
                                                  Select(column => (column.ColumnName + (withTypes ? separator + column.DataType.ToString() : "")));
                sb.AppendLine(string.Join(separator.ToString(), columnNames));

                foreach (DataRow row in dt.Rows)
                {
                    IEnumerable<string> fields = row.ItemArray.Select(field => $"{field.ToString().Replace("\"", "\"\"").Replace(Environment.NewLine, " ")}{(withTypes ? separator + "" : "") }");
                    sb.AppendLine(string.Join(separator.ToString(), fields));
                }

                lResult.Add(sb.ToString());
            }

            return lResult;
        }

        public static DataSet CSVtoDataSet(this List<string> collectionCSV, bool withTypes = false) //, char separator = '|')
        {    
            var ds = new DataSet();

            foreach (var csv in collectionCSV)
            {
                var dt = new DataTable();

                var readHeader = false;
                var lines = csv.Split(new[] { Environment.NewLine }, StringSplitOptions.None);

                foreach (var line in lines)
                {
                    if (!readHeader)
                    {
                        readHeader = true;
                        List<string> splited = line.Split(separator).ToList();

                        for (int i = 0; i < splited.Count; i++)
                        {
                            var columnName = splited[i];
                            var columnType = typeof(string);

                            if (withTypes && splited.Count > 1)
                            {
                                i++;
                                if (lines.Count() > 1)
                                {
                                    columnType = Type.GetType(splited[i]);
                                }
                            }

                            dt.Columns.Add(new DataColumn { ColumnName = columnName, DataType = columnType, AllowDBNull = true });
                        }
                    }
                    else
                    {
                        var splitedRow = line.Split(separator).ToList();

                        List<object> currentRow = new List<object>();

                        for (int i = 0; i < splitedRow.Count; i++)
                        {
                            if (withTypes && splitedRow.Count > 1)
                            {
                                var inputValue = splitedRow[i];
                                var t = dt.Columns[i / 2].DataType;

                                TypeConverter typeConverter = TypeDescriptor.GetConverter(t);
                                object propValue = string.IsNullOrEmpty(inputValue) ? null : typeConverter.ConvertFromString(inputValue);

                                currentRow.Add(propValue);
                                i++;//Next (0/2)
                            }
                            else
                            {
                                currentRow.Add(splitedRow[i]);
                            }
                        }

                        if (!currentRow.All(x => string.IsNullOrEmpty(x.ToString())))
                            dt.Rows.Add(currentRow.ToArray());
                    }
                }

                ds.Tables.Add(dt);
            }

            return ds;
        }
    }
}