コード例 #1
0
        /// <summary>
        /// オブジェクトから文字列としてのCSVデータを取得します
        /// </summary>
        /// <typeparam name="T"> Entityの型 </typeparam>
        /// <param name="contents"> T型オブジェクトのList </param>
        /// <returns> CSVデータ(Iterator) </returns>
        /// <exception cref="ArgumentException"></exception>
        /// <exception cref="ArgumentNullException"></exception>
        /// <exception cref="ArgumentOutOfRangeException"></exception>
        /// <exception cref="NotSupportedException"></exception>
        /// <exception cref="TypeLoadException"></exception>
        /// <exception cref="AmbiguousMatchException"></exception>
        /// <exception cref="RegexMatchTimeoutException"></exception>
        public IEnumerable <string> GetCsvString <T>(List <T> contents)
            where T : new()
        {
            PropertyInfo[] properties = typeof(T).GetProperties();
            string[]       propNames  = properties.Select((x) => x.Name).ToArray();

            // T型オブジェクトの情報をstringのListに変換するローカル関数
            List <string> getValues(T obj)
            {
                var l = new List <string>(propNames.Length);

                foreach (string n in propNames)
                {
                    l.Add(typeof(T).GetRuntimeProperty(n).GetValue(obj).ToString());
                }

                return(l);
            };

            // ヘッダーを出力する場合
            if (HasHeader)
            {
                string header = string.Empty;

                foreach (var prop in properties)
                {
                    // Propertyに紐付いた属性値を取得
                    HeaderAttribute header_atrb =
                        prop.GetCustomAttribute <HeaderAttribute>();

                    if (header_atrb != null &&
                        (!string.IsNullOrWhiteSpace(header_atrb.Name)))
                    {
                        // 属性値が設定されていて、属性値が空文字・空白でない場合
                        // ヘッダーとする
                        header += header_atrb.Name + Delimiter.ToString();
                    }
                    else
                    {
                        header += prop.Name + Delimiter.ToString();
                    }
                }

                yield return(header.Remove(header.Length - 1, 1));
            }

            // T型オブジェクトから行ごとのデータを返す
            foreach (var ctn in contents)
            {
                yield return(GetLineData(getValues(ctn)));
            }
        }
コード例 #2
0
ファイル: CsvReader.cs プロジェクト: t-okkn/Enjaxel
        /// <summary>
        /// 読み込まれたCSVデータの内容をカスタムオブジェクトで取得します
        /// </summary>
        /// <typeparam name="T"> マッピングするオブジェクトの型 </typeparam>
        /// <returns> マッピングされたオブジェクトのList </returns>
        /// <exception cref="ArgumentException"></exception>
        /// <exception cref="ArgumentNullException"></exception>
        /// <exception cref="NotSupportedException"></exception>
        /// <exception cref="MissingMethodException"></exception>
        /// <exception cref="MethodAccessException"></exception>
        /// <exception cref="InvalidCastException"></exception>
        /// <exception cref="OverflowException"></exception>
        /// <exception cref="FormatException"></exception>
        /// <exception cref="TypeLoadException"></exception>
        /// <exception cref="TargetException"></exception>
        /// <exception cref="TargetInvocationException"></exception>
        /// <exception cref="AmbiguousMatchException"></exception>
        /// <exception cref="FailedMappingException"></exception>
        public List <T> GetContents <T>() where T : new()
        {
            var res  = new List <T>();
            var maps = new List <MappingObject>();

            if (Headers.Count == 0)
            {
                return(res);
            }

            PropertyInfo[] properties = typeof(T).GetProperties();

            if (properties.Length != Headers.Count)
            {
                throw new FailedMappingException
                          ("マッピングしようとしているPropertyの数とヘッダーの数が一致しません。");
            }

            foreach (PropertyInfo prop in properties)
            {
                var map = new MappingObject();

                // Propertyに紐付いた属性値を取得
                HeaderAttribute header_atrb =
                    prop.GetCustomAttribute <HeaderAttribute>();

                if (prop.PropertyType.Name.Contains("Nullable"))
                {
                    // Nullableの型の時
                    // GetUnderlyingTypeから型を取得する
                    map.ObjectType = Nullable.GetUnderlyingType(prop.PropertyType);

                    // Nullableフラグを立てる
                    map.IsNullable = true;
                }
                else
                {
                    // Nullableの型でないときは普通にPropertyTypeから取得
                    map.ObjectType = prop.PropertyType;
                }

                if (header_atrb != null && Headers.Contains(header_atrb.Name))
                {
                    // 属性値が設定されていて、属性値に対応するヘッダーが存在している場合
                    // ヘッダーに対応するプロパティ名を取得
                    map.Name   = prop.Name;
                    map.Number = Headers.IndexOf(header_atrb.Name);
                }
                else if (Headers.Contains(prop.Name))
                {
                    // 属性値が設定されていなければヘッダーに対応するプロパティ名を
                    // 検索して取得
                    map.Name   = prop.Name;
                    map.Number = Headers.IndexOf(prop.Name);
                }
                else
                {
                    throw new FailedMappingException
                              ("ヘッダー名称がマッピングしようとしているオブジェクト内に" +
                              "存在しません。");
                }

                maps.Add(map);
            }

            // プロパティに値を設定するためのローカル関数
            void setValue(ref T obj, string propName, object value) =>
            typeof(T).GetRuntimeProperty(propName).SetValue(obj, value);

            foreach (var ctn in Contents)
            {
                // ジェネリクスのインスタンス作成
                var Tobj = Activator.CreateInstance <T>();

                foreach (var map in maps)
                {
                    // コンテンツから値を取得
                    string str = ctn[map.Number];

                    if (map.ObjectType.Equals(typeof(string)))
                    {
                        // マッピング先の型がstringならそのまま値を入れる
                        setValue(ref Tobj, map.Name, str);
                    }
                    else
                    {
                        // マッピング先の型がstring以外なら値を変換
                        TypeCode code  = Type.GetTypeCode(map.ObjectType);
                        object   value = string.IsNullOrWhiteSpace(str) ?
                                         null : str.ConvertValue(code);

                        // valueがnullで、マッピング先の型がNullableでない場合を除き
                        // 値を設定する
                        if (!(value == null && (!map.IsNullable)))
                        {
                            setValue(ref Tobj, map.Name, value);
                        }

                        // valueがnullで、マッピング先の型がNullableでない場合は
                        // マッピング先クラスのコンストラクタの初期値に依存させる
                    }
                }

                res.Add(Tobj);
            }

            return(res);
        }