В настоящее время я ищу OR-mapper для совместного проекта, который я собираюсь начать. Поскольку мы используем встроенный OR-mapper на работе, я не очень много знаю о том, как работают другие картографы (и имеют довольно неполную картину, которая существует). После некоторых исследований кажется, что NHibernate, Linq-to-SQL и Entity Framework являются наиболее часто используемыми.
Итак, вот мой вопрос: возможно ли [вставить свой любимый ORM здесь] сопоставить отношение "один ко многим" и "один к одному" между одними и теми же таблицами и как это делается (изящно)? Простым примером этого является сохранение списка элементов (один ко многим) и выбранного элемента (один к одному).
Причина, по которой я выбрал этот конкретный вопрос, заключается в том, что это больно с нашим внутренним OR-mapper: он просто не допускает более одного отношения между двумя таблицами. То, что я хочу получить от этого, - это понимание людей, которые работают с этими картографами, чтобы помочь мне решить, какой (существующий!) OR-mapper использовать для моего побочного проекта.
Спасибо за вашу помощь!
Я думаю, что большинство ведущих ORM поддерживают такие сопоставления (единственным исключением, которое я слышал, является Subsonic). Например, в DataObjects.Net он будет выглядеть следующим образом:
public class ItemStore : Entity
{
[Field, Key]
public int Id { get; set; }
[Field]
public Item SelectedItem { get; set; }
[Field, Association(PairTo = "Store")]
public EntitySet<Item> Items { get; private set; }
}
public class Item : Entity
{
[Field, Key]
public int Id { get; set; }
[Field]
public ItemStore Store { get; set; }
}
Назначение OR-преобразователя состоит в том, чтобы сделать базу данных соответствующей графе объектов. Таким образом, ассоциация, которую вы описываете, может выглядеть так: (и здесь я использую Hibernate, который более или менее совпадает с NHibernate, но в Java вместо С#/. NET)
//table schema:
// item_store(item_store_id, selected_item_id)
@Entity
@Table(name="item_store")
class ItemStore {
@Id
@Column(name="item_store_id")
public String getId() {...}
@OneToMany(mappedBy="itemStore")
public Collection<Item> getItems() {...}
@ManyToOne
@JoinColumn(name="selected_item_id")
public Item getSelectedItem() {...}
}
//table schema:
// item(item_id, item_store_id)
@Entity
@Table(name="item")
class Item {
@Id
@Column(name="item_id")
public String getId() {...}
@ManyToOne
@JoinColumn(name="item_store_id")
public ItemStore getItemStore() {...}
}
Я уверен, что я где-то ошибся, но надеюсь, вы поймете, как это работает.
Если у вас две таблицы, одна для списков и одна для ListItems. ListItems будет иметь внешний ключ для списков и списков, которые будут иметь внешний ключ для ListItems для выбранного элемента.
Это очень простая взаимосвязь и должна поддерживаться во всех инструментах OR-mapping.