Hỏi về câu lệnh SQL trong Oracle tạo View điền khuyết thông tin

Liên hệ QC

kyo

Nguyễn Khắc Duy
Thành viên danh dự
Tham gia
4/6/06
Bài viết
901
Được thích
2,716
Gửi mọi người,

kyo có một vấn đề muốn nhờ mọi người giúp đỡ. kyo có 2 bảng dữ liệu như sau:

Bảng 1: bao gồm 3 cột LINE, STARTDATE và MOLD

upload_2017-7-13_11-46-45.png

Bảng 2: bao gồm rất nhiều cột thông tin khác, nhìn chung cũng có LINE và PRODDATE. Và bảng này là bảng có rất đầy đủ các thông tin các ngày (từ ngày 22/6 đến ngày 12/7)

Bài toán kyo muốn giải quyết là các giá trị MOLD của bảng 1 sẽ điền khuyết vào bảng 2 sau khi kyo inner join (để tạo ra bảng 3) với LINE = LINE và STARTDATE < = PRODDATE. Cụ thể là ví dụ, trong phạm vi từ ngày 22 đến 26, thông tin của bảng 3 với giá trị MOLD là A, sau đó ngày 27 thì bảng 3 điền giá trị C và ngày 28 trở đi đến ngày 12/7 sẽ điền giá trị là JA.

kyo làm câu lệnh như sau:
Select b.mold, max(startdate) as moldstart, focus_factory, proddate, a.line, bundle, week, month, EFRTMIN
from yearly_ae_model_v_2years a inner join mold_ij_used b on a.line = b.line
and (b.startdate<=proddate)
group by b.mold, focus_factory, proddate, a.line, bundle, week, month,EFRTMIN
order by proddate

Tuy nhiên kết quả sau cùng thì nó bị trùng lắp khi qua ngày 27, cụ thể nó sẽ xuất hiện cả MOLD A và C (mong muốn là ngày 27 chỉ có MOLD C mà thôi), rồi ngày 28 thì xuất hiện cả 3 MOLD luôn (mong muốn là ngày 28 chỉ có MOLD JA).

upload_2017-7-13_12-5-32.png

Mọi người giúp kyo chỉnh lại câu lệnh SQL với (kyo dùng SQL trong Oracle).

Cảm ơn mọi người.
 
Gửi mọi người,

kyo có một vấn đề muốn nhờ mọi người giúp đỡ. kyo có 2 bảng dữ liệu như sau:

Bảng 1: bao gồm 3 cột LINE, STARTDATE và MOLD

View attachment 179501

Bảng 2: bao gồm rất nhiều cột thông tin khác, nhìn chung cũng có LINE và PRODDATE. Và bảng này là bảng có rất đầy đủ các thông tin các ngày (từ ngày 22/6 đến ngày 12/7)

Bài toán kyo muốn giải quyết là các giá trị MOLD của bảng 1 sẽ điền khuyết vào bảng 2 sau khi kyo inner join (để tạo ra bảng 3) với LINE = LINE và STARTDATE < = PRODDATE. Cụ thể là ví dụ, trong phạm vi từ ngày 22 đến 26, thông tin của bảng 3 với giá trị MOLD là A, sau đó ngày 27 thì bảng 3 điền giá trị C và ngày 28 trở đi đến ngày 12/7 sẽ điền giá trị là JA.

kyo làm câu lệnh như sau:


Tuy nhiên kết quả sau cùng thì nó bị trùng lắp khi qua ngày 27, cụ thể nó sẽ xuất hiện cả MOLD A và C (mong muốn là ngày 27 chỉ có MOLD C mà thôi), rồi ngày 28 thì xuất hiện cả 3 MOLD luôn (mong muốn là ngày 28 chỉ có MOLD JA).

View attachment 179502

Mọi người giúp kyo chỉnh lại câu lệnh SQL với (kyo dùng SQL trong Oracle).

Cảm ơn mọi người.
Kyo thêm 1 cái join nữa là mold của bảng 1 với mold bảng 2 thử nhé
 
  • Thích
Reactions: kyo
Là sao anh? Bảng 2 không có mold anh, chỉ có bảng 1 thôi. Mà em cần thông tin của bảng 2 và điền thêm giá trị mold của bảng 1 nên mới tạo 1 cái view (bảng 3) để xem.
 
Gửi mọi người,

kyo có một vấn đề muốn nhờ mọi người giúp đỡ. kyo có 2 bảng dữ liệu như sau:

Bảng 1: bao gồm 3 cột LINE, STARTDATE và MOLD

View attachment 179501

Bảng 2: bao gồm rất nhiều cột thông tin khác, nhìn chung cũng có LINE và PRODDATE. Và bảng này là bảng có rất đầy đủ các thông tin các ngày (từ ngày 22/6 đến ngày 12/7)

Bài toán kyo muốn giải quyết là các giá trị MOLD của bảng 1 sẽ điền khuyết vào bảng 2 sau khi kyo inner join (để tạo ra bảng 3) với LINE = LINE và STARTDATE < = PRODDATE. Cụ thể là ví dụ, trong phạm vi từ ngày 22 đến 26, thông tin của bảng 3 với giá trị MOLD là A, sau đó ngày 27 thì bảng 3 điền giá trị C và ngày 28 trở đi đến ngày 12/7 sẽ điền giá trị là JA.

kyo làm câu lệnh như sau:


Tuy nhiên kết quả sau cùng thì nó bị trùng lắp khi qua ngày 27, cụ thể nó sẽ xuất hiện cả MOLD A và C (mong muốn là ngày 27 chỉ có MOLD C mà thôi), rồi ngày 28 thì xuất hiện cả 3 MOLD luôn (mong muốn là ngày 28 chỉ có MOLD JA).

View attachment 179502

Mọi người giúp kyo chỉnh lại câu lệnh SQL với (kyo dùng SQL trong Oracle).

Cảm ơn mọi người.
Em nghĩ do anh đặt điều kiện này (b.startdate<=proddate) nên nó lậy vậy là đúng rồi, anh sửa lại (b.startdate=proddate) thử xem!!!
 
Là sao anh? Bảng 2 không có mold anh, chỉ có bảng 1 thôi. Mà em cần thông tin của bảng 2 và điền thêm giá trị mold của bảng 1 nên mới tạo 1 cái view (bảng 3) để xem.
Thường thì người ta hiết kế trong bảng 1 thêm 1 trường ID làm khóa chính, Bảng 2 cũng có thêm 1 trường ID, trường ID của bảng 1 có quan hệ 1 - nhiều với trường ID của bảng 2. Như vậy sẽ không gặp rắc rối như trường hợp trên. Còn trường hợp lấy ngày để join thì cũng chưa ổn lắm.
 
Thường thì người ta hiết kế trong bảng 1 thêm 1 trường ID làm khóa chính, Bảng 2 cũng có thêm 1 trường ID, trường ID của bảng 1 có quan hệ 1 - nhiều với trường ID của bảng 2. Như vậy sẽ không gặp rắc rối như trường hợp trên. Còn trường hợp lấy ngày để join thì cũng chưa ổn lắm.

theo tôi hiểu thì kyo muốn truy vấn kiểu này nè
Mã:
select * from yearly_ae_model_v_2years a OUTER APPLY
(select top 1 * from mold_ij_used b where a.line = b.line and b.startdate <= a.proddate
order by startdate desc) x

nhưng mà orcacle không biết có hỗ trợ OUTER APPLY ko , hên xui.
 
  • Thích
Reactions: kyo
Oracle 12c bắt đầu có Cross Appply, Outer Apply, và Lateral (Inline View). Chủ thớt muốn dùng cái nào thì cứ tự nhiên.
 
Cảm ơn mọi người, sau khi áp dụng thì kyo đã làm được với câu lệnh như sau:

select * from yearly_ae_model_v_2years a cross apply
(select * from (select * from mold_ij_used b where a.line = b.line and b.startdate <= a.proddate
order by startdate desc) where rownum=1)

Tuy nhiên 1 vấn đề khác phát sinh là khi kyo dùng create view testing as với câu lệnh trên thì Oracle báo lỗi không cho tạo view. Kyo có nghiên cứu qua một số hướng dẫn thì họ nói là chỉ có thể sử dụng join nếu muốn tạo view chứ không thể dùng apply. Không biết mọi người có hướng khắc phục nào giúp kyo với.

Cảm ơn mọi người.
 
Cảm ơn mọi người, sau khi áp dụng thì kyo đã làm được với câu lệnh như sau:



Tuy nhiên 1 vấn đề khác phát sinh là khi kyo dùng create view testing as với câu lệnh trên thì Oracle báo lỗi không cho tạo view. Kyo có nghiên cứu qua một số hướng dẫn thì họ nói là chỉ có thể sử dụng join nếu muốn tạo view chứ không thể dùng apply. Không biết mọi người có hướng khắc phục nào giúp kyo với.

Cảm ơn mọi người.
Nếu mà câu lệch SQL bình thường thì em sẽ viết như vầy, còn Oracel thì không biết sao!!
PHP:
SELECT *,f.mold from yearly_ae_model_v_2years e ;
LEFT JOIN ;
(SELECT c.startdate,d.line,d.MOLD FROM (SELECT a.startdate, MIN(b.startdate) as startdate1 FROM yearly_ae_model_v_2years a ;
LEFT JOIN ;
mold_ij_used b ON a.startdate<=b.startdate GROUP BY  a.startdate) c ;
LEFT JOIN;
mold_ij_used d ON c.startdate1=d.startdate) f  ON e.line=f.line AND f.startdate=e.startdate
 
Tôi trông sơ thì có vẻ bạn muốn lấy mọt cái ngày startdate gần ngày proddate nhất.
Trường hợp này có thể thử cách tính min(proddate - startdate)
 
Nếu mà câu lệch SQL bình thường thì em sẽ viết như vầy, còn Oracel thì không biết sao!!
PHP:
SELECT *,f.mold from yearly_ae_model_v_2years e ;
LEFT JOIN ;
(SELECT c.startdate,d.line,d.MOLD FROM (SELECT a.startdate, MIN(b.startdate) as startdate1 FROM yearly_ae_model_v_2years a ;
LEFT JOIN ;
mold_ij_used b ON a.startdate<=b.startdate GROUP BY  a.startdate) c ;
LEFT JOIN;
mold_ij_used d ON c.startdate1=d.startdate) f  ON e.line=f.line AND f.startdate=e.startdate

ủa trước khi xuống dòng phải đặt dấu ";" hả bạn ? đây là hệ CSDL nào bá đạo vậy bạn ? Chứ trong hệ thống SQL Server tôi chưa nhìn thấy. Xin bạn minh thị cho tôi được mở rộng hiểu biết. +-+-+-++-+-+-+
 
ủa trước khi xuống dòng phải đặt dấu ";" hả bạn ? đây là hệ CSDL nào bá đạo vậy bạn ? Chứ trong hệ thống SQL Server tôi chưa nhìn thấy. Xin bạn minh thị cho tôi được mở rộng hiểu biết. +-+-+-++-+-+-+
Trong visual foxpro đấy anh ạ, tài khoản sql server của em bi khóa rồi nên em dùng fox để test, sql server thì xuống dòng bình thường!!!
 
Cảm ơn mọi người, sau khi áp dụng thì kyo đã làm được với câu lệnh như sau:



Tuy nhiên 1 vấn đề khác phát sinh là khi kyo dùng create view testing as với câu lệnh trên thì Oracle báo lỗi không cho tạo view. Kyo có nghiên cứu qua một số hướng dẫn thì họ nói là chỉ có thể sử dụng join nếu muốn tạo view chứ không thể dùng apply. Không biết mọi người có hướng khắc phục nào giúp kyo với.

Cảm ơn mọi người.

bạn nói bạn dùng chính câu lệnh trên để tạo View ? không biết là bạn muốn dùng select * để minh họa cho người khác hiểu hay thật sự đã đem chuỗi select * để tạo View ?
Hi vọng các vị nick màu đỏ không làm tôi thất vọng chứ.
Câu lệnh của bạn đương nhiên không thể dùng để tạo View nếu dùng trong môi trường SQL server . Đơn giản vì trong đó có 2 cột trùng tên (line) chứ không phải vì có OUTER APPLY.
Nếu thật sự Oracle không cho tạo View vì có OUTER APPLY thì cũng không sao , có thể chuyển truy vấn trên thành INNER JOIN dễ dàng, nó phụ thuộc mức độ ngẫu hứng của bạn. Bạn nên tự luyện xem sao.
Tôi không biết gì về dữ liệu của bạn, nhưng đoán 90 % khả năng cặp cột (line,StartDate) trong bảng mold_ij_used phải Unique, như thế là đủ để thực hiện INNER JOIN. Hoặc xui mà rớt vào 10 % khả năng còn lại cũng không sao, truy vấn có thêm chút hấp dẫn.
 
Hình như đường chuyền sản xuất này thì ở một line, khi một Mold bắt đầu thì Mold kia chấm dứt? (cán thép hay đúc cái gì đó?)
Muốn đi đường ngoại đạo hôn?
Nếu C luôn luôn start sau A và trước JA thì loại cái Mold ra khỏi group và bên kết quả thay bằng Max(Mold)
Nếu C không luôn đi sau A thì vẫn có cách: nối startdate vào trước Mold. Như vậy Max(startdateMold) sẽ đưa ra đúng cái đi sau. Bên kết quả thì tách ra trở lại.

Select SubStr(Max(To_Char(startdate, "yyyymmdd") || mold),9) as Mold, max(startdate) as moldstart, focus_factory, proddate, a.line, bundle, week, month, EFRTMIN
from yearly_ae_model_v_2years a inner join mold_ij_used b on a.line = b.line
and (b.startdate<=proddate)
group by focus_factory, proddate, a.line, bundle, week, month,EFRTMIN
order by proddate

(tuy ngoại đạo nhưng có thể dùng SQL tiêu chuẩn mà không phải dựa vào đặc tính của phiên bản nào)
 
Lần chỉnh sửa cuối:
Hổng biết rồi cuối cùng chủ thớt giải quyết ra sao nhỉ?
Bắt thường bạn Xe Hơi Làm Lại Lốp đấy. Bạn phán cái gì khiến chủ thớt bỏ chạy mất dép rồi.
 
Web KT

Bài viết mới nhất

Back
Top Bottom