1

我修改下面到字典

ALTER TABLE [Plant] 
    ADD 
    Name nvarchar(128) NULL, 
    GLN nvarchar(15) NULL, 
    LicenceInformation nvarchar(1024) NULL, 
    MondayStart smallint NULL, 
    MondayEnd smallint NULL, 
    TuesdayStart smallint NULL, 
    TuesdayEnd smallint NULL, 
    WednesdayStart smallint NULL, 
    WednesdayEnd smallint NULL, 
    ThursdayStart smallint NULL, 
    ThursdayEnd smallint NULL, 
    FridayStart smallint NULL, 
    FridayEnd smallint NULL, 
    SaturdayStart smallint NULL, 
    SaturdayEnd smallint NULL, 
    SundayStart smallint NULL, 
    SundayEnd smallint NULL 

所示的表,我想映射到像正常化平表或參考一個特別喜歡:plant.OpeningHours [DayOfWeek.Monday]

所以它有點像一個組件映射...但不完全。

Cache.ReadWrite().Region("ReferenceData"); 
Table("Plant"); 
Map(x => x.Code); 
Map(x => x.Name); 
Map(x => x.Gln); 
Map(x => x.LicenceInformation); 
Component(x => x.OpeningHours, x => 
{ 
    //?? 
}); 

回答

1

您需要創建自己的用戶類型爲這樣:

public class CustomDictionaryType : IUserType 
{ 
    public CustomDictionaryType() 
    { 
     SqlTypes = Enumerable.Range(0, 14).Select(x => SqlTypeFactory.Int32).ToArray(); 
    } 

    public bool Equals(object x, object y) 
    { 
     // should do a key/value comparison here 
     return ReferenceEquals(x, y); 
    } 

    public int GetHashCode(object x) 
    { 
     return x.GetHashCode(); 
    } 

    public object NullSafeGet(IDataReader rs, string[] names, object owner) 
    { 
     // DayOfWeek.Sunday = 0, so have to shift days down by one since we start with Monday in our columns 
     return names.Select((x, i) => new {DayOfWeek = GetDay(i/2), value = (int) rs[x]}) 
      .GroupBy(x => x.DayOfWeek, x => x.value) 
      .ToDictionary(g => g.Key, g => new PlantOpeningHours 
               { 
                DayOfWeek = g.Key, 
                StartMinutes = g.First(), 
                DurationMinutes = g.First() - g.Last() 
               }); 
    } 

    private DayOfWeek GetDay(int index) 
    { 
     return (DayOfWeek) ((index + 6)%7); 
    } 

    public void NullSafeSet(IDbCommand cmd, object value, int index) 
    { 
     var map = value as IDictionary<DayOfWeek, PlantOpeningHours>; 
     if (map == null) 
      throw new ArgumentException("Cannot handle null dictionary"); 
     for(var i = 0; i < 7; i++) 
     { 
      var day = GetDay(i); 
      var entry = map[day]; 
      ((IDataParameter) cmd.Parameters[index + i*2]).Value = entry.StartMinutes; 
      ((IDataParameter) cmd.Parameters[index + i*2 + 1]).Value = entry.StartMinutes + entry.DurationMinutes; 
     } 
    } 

    public object DeepCopy(object value) 
    { 
     return new Dictionary<DayOfWeek, PlantOpeningHours>((IDictionary<DayOfWeek, PlantOpeningHours>) value); 
    } 

    public object Replace(object original, object target, object owner) 
    { 
     return new Dictionary<DayOfWeek, PlantOpeningHours>((IDictionary<DayOfWeek, PlantOpeningHours>)original); 
    } 

    public object Assemble(object cached, object owner) 
    { 
     return DeepCopy(cached); 
    } 

    public object Disassemble(object value) 
    { 
     return DeepCopy(value); 
    } 

    public SqlType[] SqlTypes { get; private set; } 
    public Type ReturnedType { get { return typeof (IDictionary<DayOfWeek, PlantOpeningHours>); } } 
    public bool IsMutable { get { return true; } } 
} 

當你映射它,你將需要以指定的列:

var propMap = x.Map(t => t.Duration).CustomType<CustomDictionaryType>() 
    .Columns.Clear(); 
for(var i = 0; i < 7; i++) 
{ 
    var day = (DayOfWeek) ((i + 6)%7); 
    propMap.Columns.Add(day + "Start"); 
    propMap.Columns.Add(day + "Duration"); 
} 
+0

我插入到上述情況。它給我︰NHibernate.MappingException:屬性映射具有錯誤的列數:Namespace.Mvc.Core.Model.Plant.OpeningHours類型:CustomDictionaryType不知道它期望多少列 – Sam

+0

for循環pro pMap.Columns.Count返回1 ... not 14.似乎每個.Column(...)調用都覆蓋最後一個? (var i = 0; i <7; i ++) – Sam

+0

將其更改爲: (var i = 0; i <7; i ++) { var day =(DayOfWeek)((i + 6)%7)propMap.Columns.Add(day +「Start」);propMap.Columns.Add(day +「Duration」); } – Sam