JavaRush /Kurslar /All lectures for UZ purposes /Foydali ma'lumotlar mapping ssenariylari

Foydali ma'lumotlar mapping ssenariylari

All lectures for UZ purposes
Daraja, Dars
Mavjud

Enum mapping

Primtiv ma'lumot turlarini qanday map qilishni allaqachon bilamiz: @Column annotatsiyasi va @Type annotatsiyasidan foydalanamiz. Lekin bularning barchasini bu annotatsiyalar bilan qoplash mumkin emas. Eng ko'p uchraydigan holat - bu enum.

Java'dagi enum turidagi obyektlar bazada ikki shaklda saqlanishi mumkin:

  • son sifatida
  • string sifatida

Keling, kichik bir misol yozamiz, unda foydalanuvchining sevimli rangi enum yordamida ko'rsatiladi.


enum Color {
   RED,
   ORANGE,
   YELLOW,
   GREEN,
   BLUE,
   VIOLET
}

Va User klassiga rang maydonini qo'shamiz:


@Entity
@Table(name="user")
class User
{
   @Column(name="id")
   public Integer id;
 
   @Column(name="favorite_color")
   public Color favoriteColor;
 
   @Column(name="created_date")
   public Date createdDate;
}

Agar biz xohlasak, Hibernate Color turini bazaga son sifatida saqlasin, unda favoriteColor maydoniga quyidagi annotatsiyani qo'shish kerak:


@Enumerated(EnumType.ORDINAL)

Agar qiymatlar string sifatida saqlanishini xohlasak, quyidagi annotatsiyani qo'shish kerak:


@Enumerated(EnumType.STRING)

Misol:


@Entity
@Table(name="user")
class User
{
   @Column(name="id")
   public Integer id;
 
   @Enumerated(EnumType.ORDINAL) //qiymat bazaga son sifatida saqlanadi
   @Column(name="favorite_color")
   public Color favoriteColor;
 
   @Column(name="created_date")
   public Date createdDate;
}

Boolean mapping

Ikkinchi foydali ssenariy - bu Boolean turini map qilish. Tarixan shunday bo'lgan, SQLda o'zining Boolean ma'lumot turi yo'q va uning o'rniga har qanday narsani foydalanishadi.

Uchta eng ko'p uchraydigan variantlar:

  • 1 yoki 0
  • ‘F’ yoki ‘T’
  • ‘Y’ yoki ‘N’

Umuman olganda, agar bazani o'zing loyihalashtirayotgan bo'lsang, BIT turini yozib qo'ygan ma'qul. To'liq mapping esa quyidagicha ko'rinadi:


	@Column(name = "is_correct", columnDefinition = "BIT")
	@Type(type = "org.hibernate.type.NumericBooleanType")
    private Boolean isCorrect;

Agar bazani sen loyihalashmasang, tepadagi jadvalga qarab to'g'ri turini qanday map qilishni o'ylab top.

Hisoblangan maydonlar

Ba'zida Entity klassining maydonlari soni va jadvaldagi ustunlar soni mos kelmaydi. Buning bir qator sabablari bo'lishi mumkin.

Eng keng tarqalgan sababi - Entity klassimizda biz bazaga saqlashni xohlamaydigan maydon bor. Bu juda tushunarli - bu maydonga @Transient annotatsiyasini qo'sh va Hibernate uni bazaga ishlashda e'tibordan chetda qoldiradi.

Misol:


@Entity(name = "Square")
public class Square {
           	@Id
           	public Long id;
 
           	public Integer width;
 
           	public Integer height;
 
           	@Transient
           	public Integer total;
}

Bu yaxshi variant, lekin bazadan obyektni o'qishda total maydoni null bo'ladi. Biz esa, u width*height mahsulini o'z ichiga olishini xohlardik. Buni Hibernate'da ham amalga oshirish mumkin. Bu uchun maxsus @Formula annotatsiyasi mavjud.


@Entity(name = "Square")
public class Square {
           	@Id
           	public Long id;
 
           	public Integer width;
 
           	public Integer height;
 
           	@Formula(value = " width * height ")
          	public Integer total;
}

Bunday maydon bazaga saqlanmaydi, balki bazadan obyektni o'qishda formula orqali hisoblangan qiymat bilan to'ldiriladi.

SQL so'rov quyidagicha ko'rinadi:

 SELECT id, width, height, (width* height) AS total FROM Square;

@Embedded

Yana bir foydali annotatsiya bu @Embedded. U yordamida qismi obyektning maydonlarini Entity klassining o'zidagi maydonlar sifatida ko'rib chiqish mumkin.

Aytaylik, senga User klassi bor va sen unda manzil qo'shmoqchi bo'lding:


@Entity
@Table(name="user")
class User
{
   @Column(name="id")
    public Integer id;
 
   @Column(name="user_address_country")
   public String country;
   @Column(name="user_address_city")
   public String city;
   @Column(name="user_address_street")
   public String street;
   @Column(name="user_address_home")
   public String home;
 
   @Column(name="created_date")
    public Date createdDate;
}

Hammasi yaxshi ko'rinadi, lekin Java nuqtai nazaridan manzilni alohida klassga chiqarish mantiqan to'g'ri. Chunki manzil alohida bir entity. Lekin bu qanday amalga oshiriladi, agar bazada barcha bu ma'lumot user jadvalida saqlansa?

Bizga @Embedded annotatsiyasi yordam beradi. Avval UserAddress klassini yaratamiz va unda foydalanuvchining manziliga tegishli barcha ma'lumotlarni chiqaramiz:


@Embeddable
class UserAddress
{
   @Column(name="user_address_country")
   public String country;
   @Column(name="user_address_city")
   public String city;
   @Column(name="user_address_street")
   public String street;
   @Column(name="user_address_home")
   public String home;
}

Va keyin ushbu klassning maydonini User klassimizda foydalanamiz:


@Entity
@Table(name="user")
class User
{
   @Column(name="id")
   public Integer id;
 
   @Embedded
   public UserAddress address;
 
   @Column(name="created_date")
   public Date createdDate;
}

@Embedded annotatsiyasi tufayli obyektni saqlashda Hibernate UserAddress klassining maydonlarini User klassining o'zidagi maydonlar sifatida ishlov berishni tushunadi.

Diqqat! Agar sen User klassingda ikkita UserAddress maydonini qo'shishni qaror qilsang, unda @Embedded dan foydalanishning iloji bo'lmaydi: senga maydonlar dublikat bo'ladi va ularni qandaydir tarzda ajratish kerak bo'ladi. Bu annotatsiyalarni qayta yozish bilan amalga oshiriladi: @AttributeOverrides annotatsiyasidan foydalanish orqali.

Senga shuni bilish yoqadi, ammo biz bu yerda barchasini batafsil muhokama qilishni rejalashtirmaymiz. O'ylaymanki, buning o'zi boshingni qotirish uchun etarli. Qiziqqanlar uchun rasmiy hujjat manzilini qoldiraman.

Izohlar
TO VIEW ALL COMMENTS OR TO MAKE A COMMENT,
GO TO FULL VERSION