2015-12-17 12 views
6

Tôi có một bảng thông báo chứa trường id tin nhắn, trường id ngôn ngữ và trường văn bản. Ứng dụng cần hiển thị thông báo dựa trên id và ngôn ngữ cùng nhau tạo thành khóa duy nhất. Tất cả các tin nhắn tồn tại cho ngôn ngữ EN, nhưng không phải tất cả đã được dịch sang các ngôn ngữ khác. Vì vậy, đối với tiếng Anh sẽ luôn có một bản ghi được chọn. Nhưng nếu người dùng là tiếng Pháp và ứng dụng cần hiển thị thông báo số 17 và nó chưa tồn tại đối với tiếng Pháp, tôi muốn trả lại thông điệp # 17 trong EN. Tôi muốn thực hiện điều này trong một truy vấn SELECT, tốt nhất là không có IF Báo cáo.Máy chủ SQL: cách trả về 1 hàng mặc định nếu điều kiện không đáp ứng

CHỈNH SỬA: dựa trên câu trả lời được gửi - cần phải làm rõ rằng mọi thông điệp được dịch sang khoảng 10 ngôn ngữ, có thể nhiều hơn. có nên luôn là chính xácmột hàng được trả lại dựa trên id thư và id lang. nhưng nếu hàng đó không tồn tại, tin nhắn tiếng Anh phải được trả về.

Mã cuối cùng:
declare @msgid int=2, @langid varchar(2)='fr' SELECT isnull(xx.msg, en.msg) msgtext FROM appmessages en LEFT JOIN appmessages xx ON en.msgid = xx.msgid and [email protected] WHERE en.langid = 'en' and [email protected]

Trả lời

7

Bạn có thể sử dụng một LEFT JOINISNULL để đạt

SELECT 
    ISNULL(fr.message, en.message) AS message 
FROM message_table en 
LEFT JOIN message_table fr ON 
    fr.message_id = en.message_id 
    AND fr.language = 'French' 
WHERE 
    en.message_id = 17 
    AND en.language = 'English' 
+0

vui lòng xem Chỉnh sửa của tôi. cần giải pháp nơi lang không được mã hóa cứng – lvk

+0

@lkjp Làm thế nào để bạn biết ngôn ngữ nào bạn muốn? Bạn có thể thay thế 'tiếng Pháp' bằng tham số và gọi mọi thứ theo cách đó 'AND fr.language = @ primary' – ChrisStillwell

+0

Cảm ơn. đó là những gì tôi đang tìm kiếm. – lvk

3
DECLARE @UserLanguageID char(2)='fr', 
     @DefaultLanguageID char(2)='en' 

SELECT 
    COALESCE(uMsg.KeyField, dMsg.KeyField) AS KeyField, 
    COALESCE(uMsg.LanguageID, dMsg.LanguageID) AS LanguageID, 
    COALESCE(uMsg.Text, dMsg.Text) AS Text 
FROM 
    Messages dMsg 
     LEFT JOIN Messages uMsg 
      ON uMsg.KeyField=dMsg.KeyField 
WHERE 
    ([email protected] OR [email protected]) 

    AND uMsg.La[email protected] 
    AND [email protected] 
5

Một phương pháp đơn giản này chỉ sử dụng order by cho việc ưu tiên:

select top 1 mt.* 
from message_table mt 
where mt.message_id = 17 and mt.language in ('French', 'English') 
order by (case when mt.language = 'French' then 1 else 2 end); 

Đối với một tin nhắn đơn, hiệu suất được tối ưu hóa với chỉ mục trên message_table(message_id, language). Các order by trên hai hàng là tầm thường, vì vậy nó phải rất nhanh.

Cách tiếp cận này cũng có đặc điểm đẹp mà nó hoạt động ngay cả khi một số thư không có bản dịch tiếng Anh. Nó cũng khá đơn giản để thêm các ngôn ngữ bổ sung, và hiệu quả về thời gian xử lý nên tối thiểu.

Đối với nhiều thư, bạn có thể làm điều gì đó tương tự với chức năng cửa sổ, nhưng đó sẽ là một câu hỏi khác.

+0

vui lòng xem Chỉnh sửa của tôi. cần giải pháp nơi lang không được mã hóa cứng – lvk

+0

Thay thế một tham số như '@ lang_id' là thích hợp giống như bạn có thể đang làm với' message_id' không phải lúc nào cũng là 17. – shawnt00

+0

@ shawnt00. . . Đó là một sự thích nghi tầm thường của truy vấn này - chỉ thay thế các hằng số bằng các tham số. Bạn có thể xử lý nhiều ngôn ngữ tùy thích * cùng một lúc *, ngay cả. –

0
DECLARE @RequestedLanguageId NCHAR(2) 
DECLARE @RequestedMessageId INT 

SET @RequestedLanguageId = 'FR' 
SET @RequestedMessageId = 18 

SELECT 
    ISNULL(xx.message_text, en.message_text) AS MessageText 
FROM message_table en 
LEFT JOIN message_table xx 
    ON xx.message_id = en.message_id 
    AND xx.language_id = @RequestedLanguageId 
WHERE (en.language_id = 'EN') 
    AND (en.message_id = @RequestedMessageId) 

Biến DECLARE và SET cho phép bạn kiểm tra điều này.

0

declare @msgid int=2, @langid varchar(2)='fr' SELECT isnull(xx.msg, en.msg) msgtext FROM appmessages en LEFT JOIN appmessages xx ON en.msgid = xx.msgid and [email protected] WHERE en.langid = 'en' and [email protected]

Các vấn đề liên quan