ورود

View Full Version : یک SELECT به ظاهر ساده اما هر کار میکنم درست نمیشه!



Reborn
شنبه 06 مهر 1387, 00:56 صبح
سلام.
3 تا جدول داریم برای یک سیستم انتخاب واحد مثلا.
اولی دانشجویان، دومی کلاسها و سومی ثبت نام دانشجویان در کلاسها بهمراه نمره پایانی.
حالا میخوام یه گزارش بگیرم که دانشجویان ممتاز همه کلاسها رو بهم بده هر کار میکنم نمیشه.

از این دستور برای گزارش استفاده میکنم:



SELECT S.Name,C.Name,Max(Point)
FROM Students S
INNER JOIN Selected Se
ON S.StudentID = Se.StudentID
INNER JOIN Classes C
ON C.ClassID = Se.ClassID
GROUP BY S.Name,C.Name

اینم ساختار جداول.


CREATE TABLE Students
(
StudentID int IDENTITY,
Name char(20)
)
CREATE TABLE Classes
(
ClassID int IDENTITY,
Name char(20)
)
CREATE TABLE Selected
(
StudentID int,
ClassID int,
Point tinyint
)

پیشاپیش مرسی ...

ennovation
شنبه 06 مهر 1387, 13:03 عصر
پاسخ رو ضمیمه کردم در ضمن اسم جداول را هم همانطور که در برنامه تو هست نوشتم

موفق باشی

mannai29
شنبه 06 مهر 1387, 13:54 عصر
پاسخ رو ضمیمه کردم در ضمن اسم جداول را هم همانطور که در برنامه تو هست نوشتم

دوست عزیز آیا پاسخ خود را تست کرده اید؟
اگر از خطای syntax هم بگذریم پاسخ شما اشتباه است:

SELECT
Classes.Name,
Max(Students.Name) AS MaxOfNamechar,
Max(Selected.Point) AS MaxOfPoint
این کد یعنی در هر کلاس بزرگترین نام دانشجو و بزرگترین نمره را بده !!! نه دانشجویی که بزرگترین نمره را دارد.

یک SELECT به ظاهر ساده اما هر کار میکنم درست نمیشه!

شما ابتدا باید بزرگترین نمره را در هر کلاس مشخص کنید :

select ClassID,max(Point)
from selected
group by ClassID

سپس با Join کردن باقی جدول ها به این خروجی دا نشجویی که در آن کلاس -ClassID- آن نمره را -max(Point)- دارد استخراج کنید.
در ضمن پیشنهاد می کنم در باره مفهوم group by مطالعه کنید مفید است.
پیروز باشید.

ennovation
شنبه 06 مهر 1387, 18:16 عصر
سلام mannai29 عزیز
بله من کد رو چک کردم و کار هم میکنه !
در ضمن اینی که من نوشتم رو با ACCESS ایجاد کردم و هیچ دخالتی در نوشتن کد اون نداشتم پس شما هم مطمٌن باشید که هیچ خطای نوشتاری نداره !!!!!!!!!!!!
وقتی که من در Max(Students.Name) AS MaxOfNamechar, به جای MaxOfNamechar
بنویسم نام دانشجو هیچ مشکلی ایجاد نمیشه و جواب هم درسته
GROUP BY میتونه خیلی کارتونو راحت کنه و نمیخواد دو تا کد بنویسی
البته این نظر منه !
به خاطر اینکه مطمٍن بشم حتی مقدار دهی کردم و جواب درست گرفتم
:متفکر:

nedata
یک شنبه 07 مهر 1387, 16:44 عصر
سلام



SELECT se.studentid,s.name,a.classid,a. MAX
FROM (SELECT Classid, MAX(point) AS MAX
FROM selected
GROUP BY classid) a join selected se on
se.classid=a.classid join students s on
s.studentid=se.studentid
where se.point=a.max

mannai29
یک شنبه 07 مهر 1387, 18:07 عصر
سلام mannai29 عزیز
بله من کد رو چک کردم و کار هم میکنه !
در ضمن اینی که من نوشتم رو با ACCESS ایجاد کردم و هیچ دخالتی در نوشتن کد اون نداشتم پس شما هم مطمٌن باشید که هیچ خطای نوشتاری نداره !!!!!!!!!!!!

شما براي نام دانشجو نوشته ايد Namechar در صورتي که فيلد تعريف شده در جدول Name است . من نميدانم چگونه خطاي Syntax نديده ايد. در ضمن با اين که SQL يک زبان استاندارد است بهتر آنست که کدهاي خود را در SQL-Server تست کنيد نه Access.
البته اين موضوع مهمي نيست. بحث اصلي Group By است.

وقتی که من در Max(Students.Name) AS MaxOfNamechar, به جای MaxOfNamechar
بنویسم نام دانشجو هیچ مشکلی ایجاد نمیشه و جواب هم درسته
GROUP BY میتونه خیلی کارتونو راحت کنه و نمیخواد دو تا کد بنویسی
البته این نظر منه !
به خاطر اینکه مطمٍن بشم حتی مقدار دهی کردم و جواب درست گرفتم
خوا هش مي کنم کد هاي زير را در SQL-Server خود اجرا کنيد.


create table Tbl1(Code int,Name varchar(5),Grade int)
GO
insert into Tbl1 values(1,'s1',10)
insert into Tbl1 values(1,'s2',9)
go
select Code,max(name)as MaxName,max(Grade)as MaxGrade from Tbl1 Group By Code
GO
1 s2 10

مشاهده مي کنيد که بزرگترين نمره مربوط به S1 است در حالي که جواب چيز ديگري است! چون دراینجا مابه اشتباه گفته ايم :
در گروه کد 1 ، بزرگترين نام را بده ، و ، بزرگترين نمره را هم بده!
ديگر شما را رجوع مي دهم به پاسخ قبلي خودم.وهمچنین پاسخ دوستمان nedata .