代码之家  ›  专栏  ›  技术社区  ›  Zachary Scott

AutoMapper:如何从字符串中解析Int并根据数据类型创建规则?

  •  16
  • Zachary Scott  · 技术社区  · 14 年前

    如何编写AutoMapper将字符串字段转换为整数? 我尝试了Int32.Parse(myString),但是Int32在表达式中不可用(给出了一个错误)。

    Mapper.CreateMap<SourceClass, DestinationClass>()
          .ForMember(dest => dest.myInteger, 
                      opt => opt.MapFrom(src => src.myString));
    

    类中的类型及其相应的转换类型:

    另外,是否有任何方法可以通过使用该函数解析目标中的所有整数来泛化映射?换句话说,是否有方法为数据类型创建映射?

    编辑:

    这看起来很有希望:

    AutoMapper.Mapper.CreateMap<string, int>()
              .ConvertUsing(src => Convert.ToInt32(src));
    

    这个 post 真的很有帮助

    3 回复  |  直到 8 年前
        1
  •  22
  •   Zachary Scott    14 年前

    我最后做了这样的事:

    Mapper.CreateMap<string, int>().ConvertUsing<IntTypeConverter>();
    Mapper.CreateMap<string, int?>().ConvertUsing<NullIntTypeConverter>();
    Mapper.CreateMap<string, decimal?>().ConvertUsing<NullDecimalTypeConverter>();
    Mapper.CreateMap<string, decimal>().ConvertUsing<DecimalTypeConverter>();
    Mapper.CreateMap<string, bool?>().ConvertUsing<NullBooleanTypeConverter>();
    Mapper.CreateMap<string, bool>().ConvertUsing<BooleanTypeConverter>();
    Mapper.CreateMap<string, Int64?>().ConvertUsing<NullInt64TypeConverter>();
    Mapper.CreateMap<string, Int64>().ConvertUsing<Int64TypeConverter>();
    Mapper.CreateMap<string, DateTime?>().ConvertUsing<NullDateTimeTypeConverter>();
    Mapper.CreateMap<string, DateTime>().ConvertUsing<DateTimeTypeConverter>();
    
    Mapper.CreateMap<SourceClass, DestClass>();
    
    Mapper.Map(mySourceObject, myDestinationObject);
    

    以及它引用的类(初稿):

    // TODO: Boil down to two with Generics if possible
    #region AutoMapTypeConverters
    // Automap type converter definitions for 
    // int, int?, decimal, decimal?, bool, bool?, Int64, Int64?, DateTime
    // Automapper string to int?
    private class NullIntTypeConverter : TypeConverter<string, int?>
    {   protected override int? ConvertCore(string source)
        {   if (source == null)
                return null;
            else
            {   int result;
                return Int32.TryParse(source, out result) ? (int?) result : null;
    }   }   }
    // Automapper string to int
    private class IntTypeConverter : TypeConverter<string, int>
    {   protected override int ConvertCore(string source)
        {   if (source == null)
                throw new MappingException("null string value cannot convert to non-nullable return type.");
            else
                return Int32.Parse(source); 
    }   }
    // Automapper string to decimal?
    private class NullDecimalTypeConverter : TypeConverter<string, decimal?>
    {   protected override decimal? ConvertCore(string source)
        {   if (source == null)
                return null;
            else
            {   decimal result;
                return Decimal.TryParse(source, out result) ? (decimal?) result : null;
    }   }   }
    // Automapper string to decimal
    private class DecimalTypeConverter : TypeConverter<string, decimal>
    {   protected override decimal ConvertCore(string source)
        {   if (source == null)
                throw new MappingException("null string value cannot convert to non-nullable return type.");
            else
                return Decimal.Parse(source); 
    }   }
    // Automapper string to bool?
    private class NullBooleanTypeConverter : TypeConverter<string, bool?>
    {   protected override bool? ConvertCore(string source)
        {   if (source == null)
                return null;
            else
            {   bool result;
                return Boolean.TryParse(source, out result) ? (bool?) result : null;
    }   }   }
    // Automapper string to bool
    private class BooleanTypeConverter : TypeConverter<string, bool>
    {   protected override bool ConvertCore(string source)
        {   if (source == null)
                throw new MappingException("null string value cannot convert to non-nullable return type.");
            else
                return Boolean.Parse(source); 
    }   }
    // Automapper string to Int64?
    private class NullInt64TypeConverter : TypeConverter<string, Int64?>
    {   protected override Int64? ConvertCore(string source)
        {   if (source == null)
                return null;
            else
            {   Int64 result;
                return Int64.TryParse(source, out result) ? (Int64?)result : null;
    }   }   }
    // Automapper string to Int64
    private class Int64TypeConverter : TypeConverter<string, Int64>
    {   protected override Int64 ConvertCore(string source)
        {   if (source == null)
                throw new MappingException("null string value cannot convert to non-nullable return type.");
            else
                return Int64.Parse(source); 
    }   }
    // Automapper string to DateTime?
    // In our case, the datetime will be a JSON2.org datetime
    // Example: "/Date(1288296203190)/"
    private class NullDateTimeTypeConverter : TypeConverter<string, DateTime?>
    {   protected override DateTime? ConvertCore(string source)
        {   if (source == null)
                return null;
            else
            {   DateTime result;
                return DateTime.TryParse(source, out result) ? (DateTime?) result : null;
    }   }   }
    // Automapper string to DateTime
    private class DateTimeTypeConverter : TypeConverter<string, DateTime>
    {   protected override DateTime ConvertCore(string source)
        {   if (source == null)
                throw new MappingException("null string value cannot convert to non-nullable return type.");
            else
                return DateTime.Parse(source); 
    }   }
    #endregion
    
        2
  •  5
  •   Mayo    14 年前

    public class source
    {
      public int _myfield;
    
      public string MyField
      {
        get
        {
           return _myfield.ToString();
        }
      }
    }
    
    public class destination
    {
      public string MyField { get; set; }
    }
    
        3
  •  1
  •   Fidan    6 年前

    只是为了保持更新。
    较新的版本可以自动进行一些简单的转换

        public class Source
        {
            public string String{ get; set; }
        }
    
        public class Target
        {
            public int Int { get; set; }
            public decimal Decimal{ get; set; }
        }
    
        [Fact]
        public void TestCustomMap()
        {
            Mapper.Initialize(cfg =>
                cfg.CreateMap<Source, Target>()
                    .ForMember(dest => dest.Int, opt => opt.MapFrom(src => src.String))
                    .ForMember(dest => dest.Decimal, opt => opt.MapFrom(src => src.String)));
    
            var target = Mapper.Instance.Map<Target>(new Source { String = "123" });
            Assert.Equal(expected: 123, actual: target.Int);
            Assert.Equal(expected: 123m, actual: target.Decimal);
    
            //This will throw an exception
            //Mapper.Instance.Map<Target>(new Source { String = "123.2" });
        }