ورود

View Full Version : نیازمنده استفاده از foreach در sql server



lifeless
سه شنبه 12 مرداد 1395, 13:10 عصر
سلام دوستان
من دو تا جدول دارم توی دیتابیس، یکی از جداول مربوط به موجودیت اصلی هستش که محصوله، یکی دیگه از جداول هم مربوط به تایپ های مختلف محصول هستن که به صورت پیش فرض بعد از ایجاد شدن هر محصول (موجودیت اصلی) ، برای هر محصول باید 10 تا تایپ (رکورد)(از 1 تا 10) در جدول دوم ذخیره شه. از قبل هم بعضی از محصولات امکان داره چند تا تایپ (کمتر از 10 تا) براشون ثبت شده باشه. بنده الان نیاز به یه کوئری دارم که جدول دوم رو چک کنه ببینه که آیا به ازای هر محصول از جدول محصولات آیا 10 تا رکورد ثبت شده؟ اگه نشده چک کنه ببینه کدوم یکی از تایپ ها ذخیره نشدن و اونا رو ذخیره کنه ( اضاقه کنه) تا تایپ ها برای اون محصول 10 تا بشن.
میشه راهنماییم کنید در این زمینه؟
ممنون

En_MK
یک شنبه 17 مرداد 1395, 09:53 صبح
شما نیاز به Cursor دارید که به ازای رکوردهایی که جوین(left join OR Right join) دوتا جدولتون داره رکورد بزنه

cherchil_hra
شنبه 23 مرداد 1395, 09:31 صبح
سلام دوستان
من دو تا جدول دارم توی دیتابیس، یکی از جداول مربوط به موجودیت اصلی هستش که محصوله، یکی دیگه از جداول هم مربوط به تایپ های مختلف محصول هستن که به صورت پیش فرض بعد از ایجاد شدن هر محصول (موجودیت اصلی) ، برای هر محصول باید 10 تا تایپ (رکورد)(از 1 تا 10) در جدول دوم ذخیره شه. از قبل هم بعضی از محصولات امکان داره چند تا تایپ (کمتر از 10 تا) براشون ثبت شده باشه. بنده الان نیاز به یه کوئری دارم که جدول دوم رو چک کنه ببینه که آیا به ازای هر محصول از جدول محصولات آیا 10 تا رکورد ثبت شده؟ اگه نشده چک کنه ببینه کدوم یکی از تایپ ها ذخیره نشدن و اونا رو ذخیره کنه ( اضاقه کنه) تا تایپ ها برای اون محصول 10 تا بشن.
میشه راهنماییم کنید در این زمینه؟
ممنون

به فرض اینکه شما سه جدول داشته باشی Type (نوع)، Product (محصول) و Product_Type (نوع هر محصول)

من این سه جدول را در حافظه با این مقادیر ایجاد می کنم:
DECLARE @Type TABLE (TypeID INT IDENTITY(1,1), Title VARCHAR(10))
DECLARE @Product TABLE (ProductID INT IDENTITY(1,1), Title VARCHAR(20))
DECLARE @Product_Type TABLE (Product_TypeID INT IDENTITY(1,1), MainID_FK INT,TypeID_FK INT);

INSERT INTO @Type
VALUES ('01'),('02'),('03'),('04'),('05'),('06'),('07'),( '08'),('09'),('10')

INSERT INTO @Product
VALUEs('a'),('b'),('c'),('d'),('e'),('f'),('g'),(' h'),('i'),('j')

INSERT INTO @Product_Type
VALUES (1,1) ,(1,2) ,(1,3) ,(1,4) ,(1,5) ,(1,6) ,(1,7) ,(1,8) ,(1,9) ,(1,10)
,(2,1) ,(2,2) ,(2,3) ,(2,4)
,(3,1)
--, ProductID 4
,(5,1) ,(5,2) ,(5,3) ,(5,4) ,(5,5) ,(5,6) ,(5,7) ,(5,8) ,(5,9) ,(5,10)
,(6,1) ,(6,2) ,(6,3) ,(6,4) ,(6,5) ,(6,6) ,(6,7)
,(7,6) ,(7,7) ,(7,8) ,(7,9) ,(7,10)
,(8,1) ,(8,2) ,(8,3) ,(8,4) ,(8,5) ,(8,6) ,(8,7) ,(8,8) ,(8,9) ,(8,10)
,(9,9) ,(9,10)
,(10,1),(10,2),(10,3),(10,4),(10,5),(10,6),(10,7), (10,8),(10,9)


راه حل:
1. به ازای هر محصول باید تمامی نوع ها را داشته باشیم. بنابراین جدول های product و Type را به صورت cross join می نویسیم.
2. لیست بدست آمده را با جدول واسط مرتبط می سازیم. برای حفظ مقادیر از Left Join استفاده می کنیم تا TypeIDها و ProductID هایی که در جدول واسط وجود ندارند باعث از بین رفتن مقادیر قبلی نشوند.
3. مقادیر مانده (آنهایی که مقدار id آنها null می باشد) را در جدول واسط درج می کنیم. mt.Product_TypeID IS NULL
اگر جدول واسط شما ID مختص به خود را ندارد می توانید مقادیر ProductID_FK یا TypeID_FK این جدول را در شرط قرار دهید.

INSERT INTO @Product_Type
(
MainID_FK,
TypeID_FK
)
SELECT m.ProductID,t.TypeID
FROM @Product m
CROSS JOIN @Type t
LEFT JOIN @Product_Type mt
ON t.TypeID = mt.TypeID_FK
AND m.ProductID = mt.MainID_FK
WHERE mt.Product_TypeID IS NULL


موفق باشید!