PDA

View Full Version : آموزش: ویرایش یک کوئری ! (خواندن کوچکترین مقدار column)



yeksib
پنج شنبه 29 فروردین 1392, 20:00 عصر
من میخوام توی یک جدول زیر کوچکترین مقدار رو از بین دو تا قیمت وارد شده بکشم بیرون !
sql این چطوری باید نوشته بشه !؟

بطوری که اول میاد توی Pid های یکسان بین دو تیبل price1 و price2 کوچکترین مقدار رو میکشه بیرون ! یعنی توی pid =2 میاد 1000 رو چاپ میکنه !



ID | Pid | price1 | price2
----------+--------------+------------------+----------
1 | 2 | 1000 | 6000
2 | 2 | 0 | 5000
3 | 3 | 0 | 1000
4 | 3 | 0 | 7000
5 | 4 | 5000 | 9000
6 | 4 | 2000 | 8000
7 | 4 | 3000 | 1000
8 | 4 | 3000 | 1500

MMSHFE
پنج شنبه 29 فروردین 1392, 20:22 عصر
SELECT `id`,`pid`,LEAST(`price1`,`price2`) AS `min_price` FROM `table`

yeksib
پنج شنبه 29 فروردین 1392, 20:31 عصر
SELECT `id`,`pid`,LEAST(`price1`,`price2`) AS `min_price` FROM `table`

ولی این که متاسفانه min یعنی کوچکترین مقدار رو نمیخونه !؟

MMSHFE
پنج شنبه 29 فروردین 1392, 20:51 عصر
این کوئری که دادم، توی هر سطر به شما از بین price1 و price2 اونی که کمتره رو برمیگردونه. اما اگه کلی میخواین، این کوئری رو استفاده کنید:
SELECT `pid`,MIN(`min_price`) AS `min` FROM (SELECT `id`,`pid`,LEAST(`price1`,`price2`) AS `min_price` FROM `table`) AS `temp` GROUP BY `pid`

yeksib
پنج شنبه 29 فروردین 1392, 21:25 عصر
این کوئری که دادم، توی هر سطر به شما از بین price1 و price2 اونی که کمتره رو برمیگردونه. اما اگه کلی میخواین، این کوئری رو استفاده کنید:
SELECT `pid`,MIN(`min_price`) AS `min` FROM (SELECT `id`,`pid`,LEAST(`price1`,`price2`) AS `min_price` FROM `table`) AS `temp` GROUP BY `pid`

من هر چی تستش میکنم جواب نمیده ! نمی دونم مشکلش کجاست ! شما خودتون تستش کردید!؟

MMSHFE
پنج شنبه 29 فروردین 1392, 22:51 عصر
ببینید من هر دو رو تست کردم. اگه شما میخواین توی هر رکورد بگه کمترین مقدار کدومه، کوئری اول و اگه کمترین مقدار کل رو برای هر pid میخواین، کوئری دوم جواب میده. این هم کدی که تست کردم:


mysql_connect('localhost', 'root', '');
mysql_select_db('test');
$result = mysql_query('SELECT `id`,`pid`,LEAST(`price1`,`price2`) AS `min_price` FROM `table`');
while($row = mysql_fetch_assoc($result)) {
echo '<p>' . print_r($row, 'true') . '</p>' . PHP_EOL;
}
echo '<p>-----</p>' . PHP_EOL;
$result = mysql_query('SELECT `pid`,MIN(`min_price`) AS `min` FROM (SELECT `id`,`pid`,LEAST(`price1`,`price2`) AS `min_price` FROM `table`) AS `temp` GROUP BY `pid`');
while($row = mysql_fetch_assoc($result)) {
echo '<p>' . print_r($row, 'true') . '</p>' . PHP_EOL;
}

اینم نمونه خروجی که بر اساس مقادیری که گذاشتین گرفتم:


Array ( [id] => 1 [pid] => 2 [min_price] => 1000 )
Array ( [id] => 2 [pid] => 2 [min_price] => 0 )
Array ( [id] => 3 [pid] => 3 [min_price] => 0 )
Array ( [id] => 4 [pid] => 3 [min_price] => 0 )
Array ( [id] => 5 [pid] => 4 [min_price] => 5000 )
Array ( [id] => 6 [pid] => 4 [min_price] => 2000 )
Array ( [id] => 7 [pid] => 4 [min_price] => 1000 )
Array ( [id] => 8 [pid] => 4 [min_price] => 1500 )
-----
Array ( [pid] => 2 [min] => 0 )
Array ( [pid] => 3 [min] => 0 )
Array ( [pid] => 4 [min] => 1000 )

yeksib
پنج شنبه 29 فروردین 1392, 23:14 عصر
ببینید من هر دو رو تست کردم. اگه شما میخواین توی هر رکورد بگه کمترین مقدار کدومه، کوئری اول و اگه کمترین مقدار کل رو برای هر pid میخواین، کوئری دوم جواب میده. این هم کدی که تست کردم:


mysql_connect('localhost', 'root', '');
mysql_select_db('test');
$result = mysql_query('SELECT `id`,`pid`,LEAST(`price1`,`price2`) AS `min_price` FROM `table`');
while($row = mysql_fetch_assoc($result)) {
echo '<p>' . print_r($row, 'true') . '</p>' . PHP_EOL;
}
echo '<p>-----</p>' . PHP_EOL;
$result = mysql_query('SELECT `pid`,MIN(`min_price`) AS `min` FROM (SELECT `id`,`pid`,LEAST(`price1`,`price2`) AS `min_price` FROM `table`) AS `temp` GROUP BY `pid`');
while($row = mysql_fetch_assoc($result)) {
echo '<p>' . print_r($row, 'true') . '</p>' . PHP_EOL;
}

اینم نمونه خروجی که بر اساس مقادیری که گذاشتین گرفتم:


Array ( [id] => 1 [pid] => 2 [min_price] => 1000 )
Array ( [id] => 2 [pid] => 2 [min_price] => 0 )
Array ( [id] => 3 [pid] => 3 [min_price] => 0 )
Array ( [id] => 4 [pid] => 3 [min_price] => 0 )
Array ( [id] => 5 [pid] => 4 [min_price] => 5000 )
Array ( [id] => 6 [pid] => 4 [min_price] => 2000 )
Array ( [id] => 7 [pid] => 4 [min_price] => 1000 )
Array ( [id] => 8 [pid] => 4 [min_price] => 1500 )
-----
Array ( [pid] => 2 [min] => 0 )
Array ( [pid] => 3 [min] => 0 )
Array ( [pid] => 4 [min] => 1000 )



خوب درسته ولی این داره 0 ها رو هم میگیره برای جلوگیری از این کار بایید چیکار کرد !

MMSHFE
پنج شنبه 29 فروردین 1392, 23:18 عصر
خوب توی اون رکوردها واقعاً صفر کمترین مقداره. مگه اینکه با WHERE شرط بگذارین که مقادیر بیشتر از صفر رو درنظر بگیره. مثال:
SELECT `id`,`pid`,LEAST(`price1`,`price2`) AS `min_price` FROM `table` WHERE (`min_price` > 0)

SELECT `pid`,MIN(`min_price`) AS `min`
FROM (
SELECT `id`,`pid`,LEAST(`price1`,`price2`) AS `min_price`
FROM `table`
WHERE (`min_price` > 0)
) AS `temp`
GROUP BY `pid`

yeksib
پنج شنبه 29 فروردین 1392, 23:32 عصر
خوب توی اون رکوردها واقعاً صفر کمترین مقداره. مگه اینکه با WHERE شرط بگذارین که مقادیر بیشتر از صفر رو درنظر بگیره. مثال:
SELECT `id`,`pid`,LEAST(`price1`,`price2`) AS `min_price` FROM `table` WHERE (`min_price` > 0)

SELECT `pid`,MIN(`min_price`) AS `min`
FROM (
SELECT `id`,`pid`,LEAST(`price1`,`price2`) AS `min_price`
FROM `table`
WHERE (`min_price` > 0)
) AS `temp`
GROUP BY `pid`


نه متاسفانه با این تغییر کلا کوئری هیچ جوابی نمیده !

MMSHFE
پنج شنبه 29 فروردین 1392, 23:41 عصر
شرمنده سریع نوشتم تست نکردم. اینها کار میکنه:
SELECT * FROM (SELECT `id`,`pid`,LEAST(`price1`,`price2`) AS `min_price` FROM `table`) AS `temp` WHERE (`min_price`>0)

SELECT `pid`,MIN(`min_price`) AS `min`
FROM (
SELECT * FROM (
SELECT `id`,`pid`,LEAST(`price1`,`price2`) AS `min_price` FROM `table`
) AS `temp` WHERE (`min_price`>0)
) AS `least`
GROUP BY `pid`

yeksib
پنج شنبه 29 فروردین 1392, 23:56 عصر
شرمنده سریع نوشتم تست نکردم. اینها کار میکنه:
SELECT * FROM (SELECT `id`,`pid`,LEAST(`price1`,`price2`) AS `min_price` FROM `table`) AS `temp` WHERE (`min_price`>0)

SELECT `pid`,MIN(`min_price`) AS `min`
FROM (
SELECT * FROM (
SELECT `id`,`pid`,LEAST(`price1`,`price2`) AS `min_price` FROM `table`
) AS `temp` WHERE (`min_price`>0)
) AS `least`
GROUP BY `pid`


خیلی خوب بود ولی این کد یک مشکل خیلی کوچیک دیگه داره ! شما Pid 3 رو مشاهده کنید کوئری مقدار صفر برمیگردونه ! یعنی رکورد هایی که فقط یکیشون پر شده باشه صفر میگره و نادیده گرفته میشن !



ID | Pid | price1 | price2
----------+--------------+------------------+----------
1 | 2 | 1000 | 6000
2 | 2 | 0 | 5000
3 | 3 | 0 | 2000
4 | 3 | 1000 | 0
5 | 4 | 5000 | 9000
6 | 4 | 2000 | 8000
7 | 4 | 3000 | 1000
8 | 4 | 3000 | 1500

MMSHFE
جمعه 30 فروردین 1392, 00:00 صبح
مطمئنید؟ من این جوابها رو گرفتم:


Array ( [id] => 1 [pid] => 2 [min_price] => 1000 )
Array ( [id] => 5 [pid] => 4 [min_price] => 5000 )
Array ( [id] => 6 [pid] => 4 [min_price] => 2000 )
Array ( [id] => 7 [pid] => 4 [min_price] => 1000 )
Array ( [id] => 8 [pid] => 4 [min_price] => 1500 )
-----
Array ( [pid] => 2 [min] => 1000 )
Array ( [pid] => 4 [min] => 1000 )

yeksib
جمعه 30 فروردین 1392, 00:06 صبح
مطمئنید؟ من این جوابها رو گرفتم:


Array ( [id] => 1 [pid] => 2 [min_price] => 1000 )
Array ( [id] => 5 [pid] => 4 [min_price] => 5000 )
Array ( [id] => 6 [pid] => 4 [min_price] => 2000 )
Array ( [id] => 7 [pid] => 4 [min_price] => 1000 )
Array ( [id] => 8 [pid] => 4 [min_price] => 1500 )
-----
Array ( [pid] => 2 [min] => 1000 )
Array ( [pid] => 4 [min] => 1000 )



خوب خدمت عرض کردم که الان pid=3 رو اصلا توی این دوتا مجموعه جوابی که توی آرایه ریخته وجود نداره ! در صورتی که باید برای pid=3 مقدار 1000 رو چاپ کنه !؟
Array ( [pid] => 2 [min] => 1000 )
Array ( [pid] => 4 [min] => 1000 )

MMSHFE
جمعه 30 فروردین 1392, 00:13 صبح
خوب کوئری داره درست کار میکنه. مسئله اینه که اگه توی فیلد عددی مقدار ندین، صفر میگذاره و صفر هم از بقیه اعداد price کمتره. تنها راه منطقی اینه بعد از اجرای کوئری فوق، یک کوئری دیگه اجرا کنید که رکوردهایی که یکی از priceهای اونها صفر هست رو پیدا کنه و price دیگه رو برگردونه. برای مثال:
(SELECT `pid`,`price1` AS `min` FROM `table` WHERE (`price2`=0)) UNION (SELECT `pid`,`price2` AS `min` FROM `table` WHERE (`price1`=0))

yeksib
جمعه 30 فروردین 1392, 00:30 صبح
خوب کوئری داره درست کار میکنه. مسئله اینه که اگه توی فیلد عددی مقدار ندین، صفر میگذاره و صفر هم از بقیه اعداد price کمتره. تنها راه منطقی اینه بعد از اجرای کوئری فوق، یک کوئری دیگه اجرا کنید که رکوردهایی که یکی از priceهای اونها صفر هست رو پیدا کنه و price دیگه رو برگردونه. برای مثال:
(SELECT `pid`,`price1` AS `min` FROM `table` WHERE (`price2`=0)) UNION (SELECT `pid`,`price2` AS `min` FROM `table` WHERE (`price1`=0))

یعنی کوئری دوم رو داخل
while($row = mysql_fetch_assoc($result)) {
echo '<p>' . print_r($row, 'true') . '</p>' . PHP_EOL;
}
ران کنم !؟ ران کردم اما جواب نداد !

MMSHFE
جمعه 30 فروردین 1392, 08:47 صبح
نه بعدش. یا اینکه UNION کنید. مثال:

(
SELECT * FROM
(
SELECT `id`,`pid`,LEAST(`price1`,`price2`) AS `min_price`
FROM `table`
) AS `temp`
WHERE (`min_price`>0)
)
UNION
(
(
SELECT `id`,`pid`,`price1` AS `min_price`
FROM `table`
WHERE (`price2`=0)
)
UNION
(
SELECT `id`,`pid`,`price2` AS `min_price`
FROM `table`
WHERE (`price1`=0)
)
)

اینطوری نوشتم خواناتر باشه.

yeksib
جمعه 30 فروردین 1392, 09:32 صبح
نه بعدش. یا اینکه UNION کنید. مثال:

(
SELECT * FROM
(
SELECT `id`,`pid`,LEAST(`price1`,`price2`) AS `min_price`
FROM `table`
) AS `temp`
WHERE (`min_price`>0)
)
UNION
(
(
SELECT `id`,`pid`,`price1` AS `min_price`
FROM `table`
WHERE (`price2`=0)
)
UNION
(
SELECT `id`,`pid`,`price2` AS `min_price`
FROM `table`
WHERE (`price1`=0)
)
)

اینطوری نوشتم خواناتر باشه.

از همکاری شما متشکرم ! اما باز هم جواب نمیده !؟

MMSHFE
جمعه 30 فروردین 1392, 10:50 صبح
فکر کنم دیگه این اون چیزی باشه که میخواین:

SELECT `pid`,MIN(`min_price`)
FROM (
SELECT `pid`,`price1` AS `min_price` FROM (SELECT * FROM `table` WHERE (`price2`=0)) AS `temp`
UNION
SELECT `pid`,`price2` AS `min_price` FROM (SELECT * FROM `table` WHERE (`price1`=0)) AS `temp`
UNION
(SELECT `pid`,MIN(`min_price`) AS `min_price`
FROM (
SELECT * FROM (
SELECT `id`,`pid`,LEAST(`price1`,`price2`) AS `min_price` FROM `table`
) AS `temp` WHERE (`min_price`>0)
) AS `temp`
GROUP BY `pid`)
) AS `temp`
GROUP BY `pid`
ORDER BY `pid`

yeksib
جمعه 30 فروردین 1392, 11:05 صبح
فکر کنم دیگه این اون چیزی باشه که میخواین:

SELECT `pid`,MIN(`min_price`)
FROM (
SELECT `pid`,`price1` AS `min_price` FROM (SELECT * FROM `table` WHERE (`price2`=0)) AS `temp`
UNION
SELECT `pid`,`price2` AS `min_price` FROM (SELECT * FROM `table` WHERE (`price1`=0)) AS `temp`
UNION
(SELECT `pid`,MIN(`min_price`) AS `min_price`
FROM (
SELECT * FROM (
SELECT `id`,`pid`,LEAST(`price1`,`price2`) AS `min_price` FROM `table`
) AS `temp` WHERE (`min_price`>0)
) AS `temp`
GROUP BY `pid`)
) AS `temp`
GROUP BY `pid`
ORDER BY `pid`


نه متاسفانه جواب نمیده ، ببینید اون کدی که بالا نوشتید که صفر ها رو هم برمیگردون خیلی سر راست بود اون رو نمیشه یه تغییری چیزی داد که جواب بده !


من یک سوالی اینجا پرسیدم دوست دارم شما جواب بدید البته اگه امکانش هست !
join با استفاده از دو column ! (http://barnamenevis.org/showthread.php?394220-join-%D8%A8%D8%A7-%D8%A7%D8%B3%D8%AA%D9%81%D8%A7%D8%AF%D9%87-%D8%A7%D8%B2-%D8%AF%D9%88-column-%21)

MMSHFE
جمعه 30 فروردین 1392, 11:19 صبح
اون سؤال دیگه رو جواب دادم ولی این کدی که گذاشتم رو جواب گرفتم ها!


+-----+------------------+
| pid | MIN(`min_price`) |
+-----+------------------+
| 2 | 1000 |
| 3 | 1000 |
| 4 | 1000 |
+-----+------------------+
3 rows in set (0.00 sec)

yeksib
چهارشنبه 04 اردیبهشت 1392, 09:39 صبح
اون سؤال دیگه رو جواب دادم ولی این کدی که گذاشتم رو جواب گرفتم ها!


+-----+------------------+
| pid | MIN(`min_price`) |
+-----+------------------+
| 2 | 1000 |
| 3 | 1000 |
| 4 | 1000 |
+-----+------------------+
3 rows in set (0.00 sec)


در جدولی که این قیمت ها بیرون کشیده میشوند یک فیلد نوع قیمت هم وجود داره ! برا ایکه بتوانیم به همراه کمترین قیمت نوع قیمت اون رو هم که یک آیدی هستش رو بیرون بکشم باید کوئری فوق رو چگونه تغییر بدیم !؟
متشکرم

MMSHFE
چهارشنبه 04 اردیبهشت 1392, 12:28 عصر
توی SELECT اولی، کنار `pid` اون فیلد رو هم با کاما اضافه کنید.

yeksib
چهارشنبه 04 اردیبهشت 1392, 12:37 عصر
توی SELECT اولی، کنار `pid` اون فیلد رو هم با کاما اضافه کنید.

اتفاقا قبل از اینکه این سوال رو مطرح کنم این کار رو انجام دادم ولی جوابی نداد و تمامی قیمت ها رو صفر برمیگردونه !

راستی یه سوال دیگه با چه دستوری میتونیم id هایی رو که در یک columen تکراری و غیر تکرای هستند رو بخونیم یعنی تکراری ها یکبار خونده بشوند!