Một cách hiệu quả để ghi nhãn cột trong cơ sở dữ liệu là gì?


30

Tôi đã sử dụng để gắn nhãn các cột trong cơ sở dữ liệu của mình như thế này:

user_id
user_name
user_password_hash

Để tránh xung đột khi tham gia hai bảng, nhưng sau đó tôi đã tìm hiểu thêm về cách đặt bí danh và tôi đã ngừng làm điều này.

Một cách hiệu quả để ghi nhãn cột trong cơ sở dữ liệu là gì? Tại sao?


Cơ sở dữ liệu nào? Cách tôi gắn nhãn trong Oracle khác với hầu hết các cơ sở dữ liệu khác do tính năng tự động chọn các cột để tham gia nếu các tên trùng khớp.
Joe

@Joe, Chà, tôi đã luôn sử dụng MySQL và SQLite3, nhưng nó nên áp dụng cho hầu hết các cơ sở dữ liệu khác.
Thomas O

@joe không bao giờ nhận thấy rằng Oracle là khác nhau. Bạn có thể cho một liên kết?
bernd_k

@bernd_k: Tôi đã thêm một số liên kết vào câu trả lời của mình , bên dưới
Joe

Câu trả lời:


33

Trong trường hợp của bạn, người dùng tiền tố là dư thừa. Chúng tôi (các nhà phát triển phụ trách) biết rằng đây là người dùng bảng, vậy tại sao lại thêm user_tiền tố vào trước mỗi trường?

Những gì tôi muốn đề nghị với bạn là làm điều đó với một cách tiếp cận tự nhiên hơn.

Đặc điểm của một người: Họ, Tên, Ngày sinh, Quốc tịch, v.v ...

Các đặc điểm của xe hơi là gì: Kiểu dáng, Năm, Màu sắc, Năng lượng, v.v ...

Cột của bạn nên được đặt tên càng tự nhiên càng tốt, nó sẽ làm cho lược đồ rõ ràng hơn cho mọi người, cho bạn và những người đến sau bạn. Đây cũng được gọi là giai đoạn Bảo trì và bất cứ điều gì bạn có thể làm để bảo trì dễ dàng hơn thường đáng để nỗ lực.


1
Vâng, nó làm tôi tức giận khi mọi người làm điều đó. Ngoài ra khi họ gọi tất cả các bảng của họ tbl_whthing.
Gaius

Điều này cũng liên quan đến khái niệm "Từ ngữ lớp học" và dường như có một số tranh luận trong cộng đồng khi Từ ngữ lớp học không phù hợp. (một từ lớp là một công cụ để: Xác định danh mục hoặc phân loại dữ liệu riêng biệt, Phân định loại dữ liệu được mô tả bằng tên dữ liệu và Mô tả phân loại chính của dữ liệu được liên kết với một yếu tố dữ liệu.)
Jon Schoding

17

Ngoài nhận xét của Spredzy, hãy gắn nhãn các khóa chính của bạn giống nhau (ID) để khi bạn viết truy vấn nhanh, bạn có thể dễ dàng nhớ lại (u.ID = c.ID) thay vì phải tìm kiếm "Có phải là countryID không , country_ID, country_ID, countryID ,? "


5
Tôi đã từng làm việc trên một cơ sở dữ liệu trong đó DBA quyết định sử dụng ID trong một số bảng và id trong các bảng khác và chúng tôi đã thiết lập MySQL để phân biệt chữ hoa chữ thường ... thời gian vui vẻ!
Toby

6
Chúng tôi thường sử dụng tablename.tablename_id. Ví dụ: car.car_id; người.person_id. Tên số ít cho bảng.
glasnt

@ Signt quyết định thông minh.
garik

1
Đây thực sự là một ý tưởng rất tồi và bạn sẽ mất khả năng sử dụng USINGmệnh đề SQL (nó chống lại thông số kỹ thuật).
Evan Carroll

9

Tôi không thể đồng ý nhiều hơn với phần phụ lục của David Hall cho câu trả lời xuất sắc của Spredzy. Đơn giản và tự nhiên là con đường để đi. Bảng nhầm lẫn không phải là một vấn đề nếu bạn đặt tên bảng một cách tự nhiên.

Không có ý nghĩa khi có users.user_id và Cars.car_id khi bạn có thể có users.id và Cars.id


7

Tôi sẽ lập luận rằng trong một lược đồ cơ sở dữ liệu, mỗi cột phải có một tên duy nhất, trên các bảng. Có nhiều lý do cho điều đó:

  • Từ quan điểm mô hình hóa: Bạn bắt đầu với một loạt các thuộc tính và bạn bình thường hóa nó thành các bảng. Theo thời gian, bạn có thể không chuẩn hóa hoặc bình thường hóa thêm hoặc giới thiệu các khung nhìn hoặc các khung nhìn cụ thể hóa, hoặc giới thiệu các bảng mới. Điều này không bao giờ là vấn đề nếu tất cả các tên cột là duy nhất.

  • Bạn có thể sử dụng cú pháp tham gia này : a JOIN b USING (a_id) JOIN c USING (a_id). Rất thuận tiện và cũng giúp với các điểm sau.

  • Nếu bạn chạy các truy vấn có nhiều liên kết hoặc tạo các khung nhìn cụ thể hóa SELECT *, bạn sẽ không bao giờ (tốt, có thể hiếm khi) có xung đột. Hãy nghĩ về việc tham gia person.name, product.name, country.namevv Urgh.

  • Nói chung, nếu bạn có các truy vấn lớn, thật khó để theo dõi ý idnghĩa của mọi nơi.


Làm thế nào bạn sẽ đặt tên cột cho tên nhân viên và tên trang web chẳng hạn? Làm thế nào bạn sẽ tránh được sự dư thừa của cột nhãn tên?
Spredzy

@Spredzy: Tôi sẽ chỉ đi với sự dư thừa.
Peter Eisentraut

1
Câu trả lời cho những mối quan tâm này: bí danh.
Jon của tất cả các giao dịch

7

Hãy xem, với ví dụ của bạn, nó sẽ trông giống như thế này:

USERS
----
id
username,
password
registration_date

Tôi sử dụng tên bảng bằng chữ hoa. Điều này cho phép tôi xác định bảng dễ dàng. Các cột tôi vừa đặt tên là mỗi cột cho những gì nó đại diện. Tôi cố gắng không sử dụng số hoặc bao gồm bất kỳ tiền tố hoặc hậu tố với nó. Điều này sẽ làm cho các truy vấn chết đơn giản và khá đơn giản.

BTW, tôi nghĩ bạn nên tìm một số phong cách bạn thích và gắn bó với nó. Nếu bạn thay đổi nó thường xuyên, thì bạn sẽ có một lược đồ DB lộn xộn hơn.


+1 cho "tìm một số phong cách bạn thích và gắn bó với nó." Tính nhất quán tốt hơn so với việc tuân thủ chính xác với bất kỳ tiêu chuẩn cụ thể nào (mặc dù nếu bạn chưa chọn một tiêu chuẩn, một số tốt hơn so với các tiêu chuẩn khác).
Jon của tất cả các giao dịch

5

Giống như những người khác, tôi khuyên bạn không nên bao gồm tên bảng như một phần của cột. Trừ khi bạn có hàng trăm bảng với hầu hết các tên cột giống nhau: nếu bạn có nhiều hàng chục bảng với một cột có tiêu đề ID, thì tất cả đều có nghĩa là tiền tố chúng với tên bảng.

Gần đây tôi đã rời một công ty nơi một trong những nhà phát triển ưa thích tiền tố các cột khóa chính và khóa ngoại với pk và fk. Điều này dẫn đến một số gớm ghiếc nơi các cột bắt đầu bằng pkfk (thường là khóa chính tổng hợp dựa trên 2 cột, trong đó một cột là khóa ngoại đối với bảng khác).


4
cái đó có được tính là fk_cluster không?
Kaji

5

Tôi đang làm việc trong một môi trường nơi mỗi tên cột bắt đầu bằng một tiền tố xuất phát từ tên bảng, đó không phải là phát minh của tôi, nhưng tôi khá hài lòng với nó.

Tên cột lý tưởng là duy nhất trên tất cả các bảng trong cơ sở dữ liệu.

Một số quan sát:

  • chúng ta chỉ cần bí danh bảng, khi các bảng được nối nhiều lần trong một câu lệnh chọn
  • nó ngăn một số lỗi khi sao chép đoạn mã, vì tên cột phải được điều chỉnh theo tên bảng
  • nó giúp hiển thị cho bảng nào một điểm khóa ngoại

Ý tưởng chung: Quan trọng nhất là tính nhất quán của từng quy ước đặt tên: - số ít so với số nhiều (ok áp dụng cho bảng và không phải cột) - xác định khóa chính và khóa ngoài (chúng xây dựng cấu trúc so với nội dung của cơ sở dữ liệu) - nhất quán khi bạn lưu trữ chuỗi và biến thể ngắn của cùng một chuỗi - phù hợp với cờ, trạng thái, v.v.


3

Tôi đồng ý với câu trả lời của Spredzy nhưng sẽ thêm rằng đó là vấn đề ưu tiên, tôi sẽ sử dụng camelCase thay vì under_score.

FirstName, LastName, v.v.


2
-1 vì CamelCase không hoạt động trong tất cả các hệ thống cơ sở dữ liệu và bạn không chỉ định hệ thống cơ sở dữ liệu. Ví dụ, tin xấu của nó là sử dụng CamelCase trong Oracle (nó sẽ yêu cầu sử dụng dấu ngoặc kép để tạo ra nó nhưng từ đó trở đi, mọi người truy cập sẽ phải nhảy qua các vòng để truy cập / sử dụng nó). Thật là một cơn ác mộng.
ScottCher

@ScottCher - Tôi không biết rằng nó không hoạt động trong Oracle, nhưng sau đó tôi không phải là một DBA của Oracle. Tôi đã nghĩ rằng nó sẽ được coi là đã cho rằng các tên cột cần tuân thủ trước tiên theo các quy tắc được đặt ra bởi DBS trong câu hỏi.
Toby

3

Trong trường hợp của Oracle, bạn sẽ muốn không tên cột 'id' hoặc 'tên' hoặc bất cứ điều gì chung.

Vấn đề là theo mặc định trong các phiên bản cũ hơn , Oracle sẽ cố gắng tham gia các bảng dựa trên các tên cột tương tự, vì vậy nếu tôi đã đặt tên tốt cho mọi thứ, thì cuối cùng tôi cũng đã chỉ định mệnh đề nối mặc định giữa các bảng của mình.

Nhưng ngay cả khi bạn không sử dụng Oracle, bằng cách không chọn các tên xuất hiện trong nhiều bảng, điều đó cũng có nghĩa là bạn không phải trải qua rắc rối về bí danh mỗi khi bạn phải chọn qua hai bảng:

SELECT
  instrument.name as instrument_name,
  instrument.abbr as instrument_abbr,
  source.name     as source_name,
  source.abbr     as source_abbr,
  ...
FROM ...

Vì vậy, nếu nhiều bảng chọn là chuẩn, các tên cột dài hơn sẽ giúp bạn nhập. (nếu bạn chỉ sử dụng một bảng mỗi lần ... bạn có thực sự cần một cơ sở dữ liệu quan hệ không?)

... và việc lưu kiểu gõ đưa chúng ta đến một vấn đề khác trong Oracle - ít nhất là trong 8i (phiên bản hiện tại khi tôi tham gia các khóa học Điều chỉnh và mô hình hóa dữ liệu của Oracle), bộ nhớ đệm của các kế hoạch thực hiện chỉ dựa trên rất nhiều ký tự đầu tiên của truy vấn (không thể nhớ giá trị chính xác ... 1024?), vì vậy nếu bạn có các truy vấn chỉ thay đổi theo một thứ gì đó ở cuối mệnh đề where và một danh sách dài các cột bạn đang trích xuất, bạn có thể chạy vào một hit hiệu năng vì nó không thể lưu trữ kế hoạch thực hiện chính xác.

Oracle đã có một hướng dẫn về việc chọn những gì họ tuyên bố là tên bảng và cột tốt, về cơ bản là hướng dẫn để xóa các chữ cái cho đến khoảng 5-8 ký tự, nhưng tôi không bao giờ quan tâm đến nó.

...

Khi mọi thứ khác đi:

  • các cột luôn là số ít (các bảng luôn ở dạng số nhiều)
  • tất cả các tên đều viết thường, chỉ trong trường hợp có trường hợp phân biệt chữ hoa chữ thường
  • như một kết quả của những điều trên, sử dụng dấu gạch dưới thay vì vỏ lạc đà.

cập nhật : đối với những người không quen thuộc với hành vi tham gia của Oracle, hãy xem ví dụ cuối cùng về Làm chủ Oracle SQL: Tham gia điều kiện , trong đó đề cập đến:

Chuyện gì đã xảy ra? Lý do nằm ở chỗ, ngoài nhà cung cấp_id, hai bảng này còn có một cặp cột khác có tên chung. Cột đó là tên. Vì vậy, khi bạn yêu cầu một phép nối tự nhiên giữa nhà cung cấp và các bảng bộ phận, phép nối đó diễn ra không chỉ bằng cách đánh đồng cột nhà cung cấp của hai bảng, mà cả cột tên từ hai bảng cũng được đánh đồng. Vì, không có tên nhà cung cấp nào giống với tên một phần của cùng một nhà cung cấp đó, nên không có hàng nào được trả về bởi truy vấn.

Theo 'cú pháp tham gia cũ' (8i trở về trước), 'THAM GIA TỰ NHIÊN' là hành vi tham gia mặc định và tôi tin rằng vẫn là nếu bạn không chỉ định điều kiện tham gia. Khi 'THAM GIA TỰ NHIÊN' là một lựa chọn chính thức trong 9i, khuyến nghị chung là không sử dụng nó , bởi vì việc đặt tên cột xấu có thể làm bạn khó chịu, đó là điều tôi ủng hộ cho các tên cột tốt.


4
Bạn đang đề cập đến "Joins tự nhiên" trong đoạn thứ hai của bạn? Nếu vậy, SHUDDER ... Bất cứ khi nào có thể, bạn nên chỉ định cách bạn muốn hệ thống cơ sở dữ liệu của mình tham gia các bảng của mình. Để nó đến cơ sở dữ liệu để quyết định có thể tạo ra kết quả bất ngờ / không nhất quán. Ngoài ra, Natural Joins bị giới hạn tham gia giữa hai bảng và do đó tương đối hạn chế về khả năng sử dụng của chúng.
ScottCher

2
THAM GIA TỰ NHIÊN chưa bao giờ là mặc định. Nếu không có phép nối rõ ràng nào được đưa ra, thì phép nối cartesian sẽ được thực hiện (tức là mỗi hàng trong một bảng được nối với mỗi và mọi hàng trong bảng khác). Trước khi các phép nối ANSI được hỗ trợ (nghĩa là các phép nối được chỉ định trong mệnh đề TỪ) các phép nối phải được thực hiện trong mệnh đề WHERE.
Gary

1
-1 cho các phép nối tự nhiên. Khi một thay đổi lược đồ không liên quan có thể phá vỡ các phép nối, hoặc tệ hơn nữa, thay đổi chúng mà không gây ra bất kỳ lỗi nào, bạn đang ở trong một thế giới đau khổ. Xin vui lòng, nghĩ về trẻ em và LUÔN LUÔN chỉ định các lĩnh vực tham gia của bạn.
Jon của tất cả các giao dịch

2
@ScottCher: "Để cơ sở dữ liệu quyết định" - trước tiên, có lẽ bạn có nghĩa là "DBMS" chứ không phải là "cơ sở dữ liệu". Thứ hai, không có cơ chế AI hoặc nhân học trong Oracle; đúng hơn, NATURAL JOINlà xác định.
onedaywhen

1
@Joe cross joinlà, đã và sẽ luôn là 'mặc định'. Oracle chưa bao giờ khớp với tên cột trừ khi natural joinđược sử dụng rõ ràng
Jack Douglas

1
  1. Không bao giờ sử dụng dấu ngoặc kép "vì khi làm như vậy, bạn ghi đè lên trường hợp gấp của cơ sở dữ liệu. Thông số SQL yêu cầu tất cả các định danh được gấp lại thành chữ hoa. Một số cơ sở dữ liệu, như PostgreSQL gấp chúng thành chữ thường. Nếu không có gì được trích dẫn, nó sẽ hoạt động trong tất cả các cơ sở dữ liệu và họ có thể xếp chúng vào thông số kỹ thuật hoặc mặc định dành riêng cho rdbms.
  2. Sử dụng under_score ( _), vì như trên - bạn không nên sử dụng camelCase.
  3. sử dụng {entity}_idcho id (và khóa ngoại trỏ đến các id đó). Bởi vì sau đó bạn có thể sử dụng USINGmệnh đề. Các tên khóa duy nhất trên toàn cầu được sử dụng trong điều kiện tham gia là một quy ước được thiết lập trong thông số kỹ thuật.

    SELECT *
    FROM employee
    INNER JOIN department
      USING (department_id);
    
      -- compare to
      ON employee.department_id = department.department_id;

1
Tôi cập nhật điều này để rõ ràng hơn.
Evan Carroll
Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.