Dấu phân cách trong MySQL


165

Tôi thường thấy mọi người đang sử dụng Dấu phân cách. Tôi đã cố gắng tìm ra những gì là dấu phân cách và mục đích của chúng là gì. Sau 20 phút googling, tôi không thể tìm được câu trả lời thỏa mãn cho mình. Vì vậy, câu hỏi của tôi là bây giờ: Dấu phân cách là gì và khi nào tôi nên sử dụng chúng?

Câu trả lời:


245

Các dấu phân cách khác với mặc định ;thường được sử dụng khi xác định hàm, thủ tục được lưu trữ và kích hoạt trong đó bạn phải xác định nhiều câu lệnh. Bạn định nghĩa một dấu phân cách khác nhau $$được sử dụng để xác định kết thúc của toàn bộ thủ tục, nhưng bên trong nó, các câu lệnh riêng lẻ được kết thúc bởi mỗi ;. Theo cách đó, khi mã được chạy trong mysqlmáy khách, máy khách có thể cho biết toàn bộ thủ tục kết thúc ở đâu và thực thi nó như một đơn vị thay vì thực thi các câu lệnh riêng lẻ bên trong.

Lưu ý rằng DELIMITERtừ khóa là một chức năng của mysqlmáy khách dòng lệnh (và một số máy khách khác) và không phải là một tính năng ngôn ngữ MySQL thông thường. Sẽ không hiệu quả nếu bạn cố chuyển nó qua API ngôn ngữ lập trình cho MySQL. Một số khách hàng khác như PHPMyAdmin có các phương thức khác để chỉ định một dấu phân cách không mặc định.

Thí dụ:

DELIMITER $$
/* This is a complete statement, not part of the procedure, so use the custom delimiter $$ */
DROP PROCEDURE my_procedure$$

/* Now start the procedure code */
CREATE PROCEDURE my_procedure ()
BEGIN    
  /* Inside the procedure, individual statements terminate with ; */
  CREATE TABLE tablea (
     col1 INT,
     col2 INT
  );

  INSERT INTO tablea
    SELECT * FROM table1;

  CREATE TABLE tableb (
     col1 INT,
     col2 INT
  );
  INSERT INTO tableb
    SELECT * FROM table2;
  
/* whole procedure ends with the custom delimiter */
END$$

/* Finally, reset the delimiter to the default ; */
DELIMITER ;

Cố gắng sử dụng DELIMITERvới một máy khách không hỗ trợ, nó sẽ khiến nó được gửi đến máy chủ, điều này sẽ báo lỗi cú pháp. Ví dụ: sử dụng PHP và MySQLi:

$mysqli = new mysqli('localhost', 'user', 'pass', 'test');
$result = $mysqli->query('DELIMITER $$');
echo $mysqli->error;

Lỗi với:

Bạn có một lỗi trong cú pháp SQL của bạn; kiểm tra hướng dẫn tương ứng với phiên bản máy chủ MySQL của bạn để biết đúng cú pháp để sử dụng gần 'DELIMITER $$' ở dòng 1


3
Các kịch bản mà nó có ý nghĩa để sử dụng một dấu phân cách là gì? Tôi đã không thực sự hiểu nó.
System.Data

2
@ System.Data Câu đầu tiên trong câu trả lời của tôi - khi xác định các thủ tục được lưu trữ, các chức năng tùy chỉnh và kích hoạt. Bất cứ lúc nào nhiều câu lệnh được thực thi như một đơn vị trên dòng lệnh MySQL.
Michael Berkowski

2
Lưu ý rằng lệnh DELIMITER không hoạt động từ SQL PhpMyAdmin (ít nhất là một số phiên bản). Thay vào đó, bạn có thể đặt dấu phân cách trong một trường riêng cho chính SQL. Điều này khiến tôi bối rối trong một thời gian khá lâu ... :-)
Rất bất thường

1
@MichaelBerkowski, Hy vọng chúng ta sẽ có cách để làm điều đó trong tương lai.
Pacerier

1
@StockB Câu trả lời này không thực sự giải thích tại sao các thủ tục được lưu trữ lại có lợi, việc đề cập đến "một đơn vị" đề cập đến cách MySQL có thể diễn giải SP khi phân tích nó: xác định ranh giới đơn vị bằng cách phân cách, sau đó phân tích các câu lệnh riêng lẻ bên trong. Nhưng vì bạn đã hỏi, sử dụng SP đa câu lệnh sẽ cho phép bạn ẩn chi tiết triển khai khỏi ứng dụng gọi SP. Mã ứng dụng không cần phải quan tâm đến những gì SQL được thực thi (và bạn có thể thay đổi nó nếu cần) miễn là nó trả về một kết quả nhất quán. Cũng giống như một hàm trong mã.
Michael Berkowski

21

Câu lệnh DELIMITER thay đổi dấu phân cách chuẩn là dấu chấm phẩy (;) sang dấu khác. Dấu phân cách được thay đổi từ dấu chấm phẩy (;) thành dấu gạch chéo kép //.

Tại sao chúng ta phải thay đổi dấu phân cách?

Bởi vì chúng tôi muốn chuyển toàn bộ thủ tục được lưu trữ, các chức năng tùy chỉnh, vv cho toàn bộ máy chủ thay vì để công cụ mysql diễn giải từng câu lệnh tại một thời điểm.


13

Khi bạn tạo một thói quen được lưu trữ có một BEGIN...ENDkhối, các câu lệnh trong khối bị chấm dứt bởi dấu chấm phẩy (;). Nhưng CREATE PROCEDUREtuyên bố cũng cần một kẻ hủy diệt. Vì vậy, nó trở nên mơ hồ cho dù dấu chấm phẩy trong cơ thể của thói quen chấm dứt CREATE PROCEDURE, hoặc chấm dứt một trong những tuyên bố trong cơ thể của thủ tục.

Cách để giải quyết sự mơ hồ là khai báo một chuỗi riêng biệt (không được xảy ra trong phần thân của thủ tục) mà máy khách MySQL nhận ra là dấu kết thúc thực sự cho CREATE PROCEDUREcâu lệnh.


1
Đây là câu trả lời tốt nhất vì nó cho biết lý do chính xác để sử dụng DELIMITER theo cách đơn giản nhất và không gây ra bất kỳ sự nhầm lẫn nào. Cảm ơn
Fakhar Anwar

6

Dấu phân cách là ký tự hoặc chuỗi ký tự mà bạn sẽ sử dụng để nói với máy khách MySQL rằng bạn đã nhập xong một câu lệnh Sql.


5

Bạn xác định DELIMITER để báo cho máy khách mysql xử lý các câu lệnh, hàm, thủ tục được lưu trữ hoặc kích hoạt dưới dạng toàn bộ câu lệnh. Thông thường trong tệp .sql bạn đặt một DELIMITER khác như $$. Lệnh DELIMITER được sử dụng để thay đổi dấu phân cách chuẩn của các lệnh MySQL (nghĩa là;). Vì các câu lệnh trong các thường trình (hàm, thủ tục được lưu trữ hoặc kích hoạt) kết thúc bằng dấu chấm phẩy (;), để coi chúng là câu lệnh ghép, chúng tôi sử dụng DELIMITER. Nếu không được xác định khi sử dụng các thường trình khác nhau trong cùng một tệp hoặc dòng lệnh, nó sẽ đưa ra lỗi cú pháp.

Lưu ý rằng bạn có thể sử dụng nhiều loại ký tự không dành riêng để tạo dấu phân cách tùy chỉnh của riêng bạn. Bạn nên tránh sử dụng ký tự dấu gạch chéo ngược (\) vì đó là ký tự thoát cho MySQL.

DELIMITER không thực sự là một lệnh ngôn ngữ MySQL, đó là lệnh máy khách.

Thí dụ

DELIMITER $$

/*This is treated as a single statement as it ends with $$ */
DROP PROCEDURE IF EXISTS `get_count_for_department`$$

/*This routine is a compound statement. It ends with $$ to let the mysql client know to execute it as a single statement.*/ 
CREATE DEFINER=`student`@`localhost` PROCEDURE `get_count_for_department`(IN the_department VARCHAR(64), OUT the_count INT)
BEGIN
    
    SELECT COUNT(*) INTO the_count FROM employees where department=the_department;

END$$

/*DELIMITER is set to it's default*/
DELIMITER ;

Bạn có thể thêm dấu phân cách để xác định phạm vi mã thủ tục mysql của bạn. Để biết thêm chi tiết, vui lòng tham khảo phần cuối của hướng dẫn của tôi techflirt.com/mysql-stored-procedure-tutorial
Ankur Kumar Singh

1

DELIMITER để báo cho máy khách mysql xử lý các câu lệnh, hàm, thủ tục được lưu trữ hoặc kích hoạt dưới dạng toàn bộ câu lệnh. Thông thường trong a. tập tin sql bạn đặt một DELIMITER khác như $$. Lệnh DELIMITER được sử dụng để thay đổi dấu phân cách chuẩn của các lệnh MySQL


1

Dấu phân cách là một ký tự trong SQL, được sử dụng để phân tách các mục dữ liệu trong cơ sở dữ liệu. Nó xác định phần đầu và phần cuối của chuỗi ký tự. Nói chung, dấu phân cách được sử dụng trong SQL là ';'.

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.