الانتقال إلى المحتوى

سؤال أرجو المساعدة به


Ashraf_id

Recommended Posts

السلام عليكم ورحمة الله وبركاته
اخواني الاعضاء أرجو مساعدني في حل هذا السؤال الذي يواجهني في أحد امتحاناتي :

طلب مني اعداد قاعدة بيانات لمكتبة في الجامعة وواجهني سؤال لم أستطع الاجابة عليه وهو :

create a function named maxBorrowing that returns all details about a student has the maximum number of borrowing in current month .

مع العلم ان هناك جدول يجب ان اعتمد عليه كالتالي :


borrowTable

student_id --- object_id --- date_of_borrow --- max_borrow_date --- Returns



وسأكون شاكرا لكم

تم تعديل بواسطة Ashraf_id
رابط هذا التعليق
شارك

اولا احنا عايزين نجيب رقم الطالب اللي بيعمل اكتر استعارات ف شهر معين وبعد كده نحط الرقم ده ف الكويري الكبير ...اوك

اولا : الحصول علي رقم الطالب ذو اكبر استعارات ف الشهر لحالي

[left]
select Student_id from (select student_id,count(*)
from borrow_Table
where date_of_borrow between(trunc(sysdate,'MM'))and(trunc(sysdate,'MM'))
group by student_id
order by count(*) desc )
where rownum<2[/left]



ثانيا وضع كل الكويري دي في كويري اكبر منها وهي اللي هتطلع بالناتج

[left]select * from students where student_id = (  select Student_id from (select student_id,count(*)
from borrow_Table
where date_of_borrow between(trunc(sysdate,'MM'))and(trunc(sysdate,'MM'))
group by student_id
order by count(*) desc )
where rownum<2   )[/left]



وشكرا

معلش الفنكشن بقه ....

create or replace function MY_Fun  is
begin 
for studentrow in (select * from students where student_id = ( select Student_id from (select student_id,count(*)
from borrow_Table
where date_of_borrow between(trunc(sysdate,'MM'))and(trunc(sysdate,'MM'))
group by student_id
order by count(*) desc )
where rownum<2 )) loop 

DBMS_OUTPUT.PUT_LINE(studentrow.student_name); 

end my_fun ;

تم تعديل بواسطة Darwiesh.fci
رابط هذا التعليق
شارك

شكرا جزيلا اخي لكن الفنكشن يجب ان يكون لها ريتيرن فاليو وانت لم تضعها فرجاءا ارجو منك اكمال الحل في القريب العاجل
وسأكون شاكرا لك

تحياتي

رابط هذا التعليق
شارك


شكرا جزيلا اخي لكن الفنكشن يجب ان يكون لها ريتيرن فاليو وانت لم تضعها فرجاءا ارجو منك اكمال الحل في القريب العاجل
وسأكون شاكرا لك

تحياتي


لم اجرب قط استرجاع اكثر من صف من خلال الفنكشن وذلك لوجود البروسيدر ..انا فقط اردت ان اوضح النقاط من خلال الرد وليست هذه الفنكشن النهائية ولكن علي حد علمي بامكانك استخدام اكثر من حل REF CURSOR او البايب تيبل اكيد في حد ف المنتدي عارفهم كويس ..لكن انا شخصيا معرفش وفوق كل زي عليم اخ اشرف

في رعاية الله
رابط هذا التعليق
شارك

  • بعد 5 أسابيع...
  • بعد 1 شهر...

السلام عليكم

هذا السؤال البسيط يخفي الكثير من العمل والتفكير بطرق وخوارزميات الحل المختلفة والتي قد تندرج من الحلول البسيطة إلى الحلول المعقدة.

سأقوم بتحليل السؤال لتقاط من أجل تبسيط مشكلة السؤال لمشاكل اصغر ومنها ننطلق للحل

1. يجب أولا بناء الاستعلام الذي يعطي رقم الطالب الأكثر استعارة للكتب خلال الشهر الحالي

2. بناء دالة function تعيد تفاصيل الطالب، أو على الأقل رقم الطالب، وهنا تتفرع الحلول من البسيطة إلى المعقدة كالتالي:
حتى لايتم فهم هذه النقطة بشكل خاطئ أقول بأنني اتفق مع الجميع بأن اي دالة لن تعيد سوى قيمة واحدة فكيف ستعيد عدة قيم؟ الجواب هو مربط الفرس.

ابسط الحلول هي بناء دالة تعيد رقم هو عدد مرات الإعارة، ويمكن الحصول على باقي تفاصيل الطالب (سأكتفي برقم الطالب) من خلال تمرير باراميتر من نوع out ليكون تعريف الدالة بالشكل التالي:

function maxBorrowing (student_id out number);



بذلك نحصل على أكثر من قيمة من الدالة، قيمة جواب الدالة، وقيمة الباراميترات.

الحل الثاني أكثر احترافية هو التفكثير بان تعيد الدالة سطر row or record (سموه ماتريدون) ويحوي التفاصيل المطلوبة.
هل يمكن ذلك؟ ... بالطبع يمكن عن طريق تعديل الدالة السابقة لتكون القيمة التي تعيدها لنا من نوع record وهذا يتطلب تعريف
SQL TYPE AS RECORD OR OBJECT
لاستخدامه في الحل.

هل هناك حلول أخرى؟؟؟
التفكير بجواب السؤال التالي يضعنا امام حل أخر ربما أكثر تعقيدا، وهو هل من الممكن ان يتساوى طالبان أو أكثر في العدد الأعظمي للإعارات في شهر معين؟
لما لا... من الممكن جدا...
إذن بنية الدالة التي ستعيد قيمة من نوع REOCRD لن تفيدنا هنا، لأن الدالة ستعيد أكثر من سطر، كل سطر سيحوي تفاصيل احد الطلاب الذين حققوا اعلى عدد من الاعارات.

بالتالي فإن هذا الحل يجبرنا على استخدام COLLECTIONS في اوراكل من أجل بناء جدول يمكن استعادته كقيمة لجواب الدالة او FUNCTION المطلوب.

هذا الحل معقد بعض الشيء، وإن كان هدف السؤال معرفة قدرة الطالب أو الموظف على تقديم حل وتعامله مع أنواع الـ TYPES و COLLECTIONS فهو أمر لابد منه، لأنه حتى في حال وجود عدة طلاب حققوا اعلى الاعارات فإن معالجته ضمن PROCEDURE OR FUNCTION منصل أمر أكثر سهولة.

اصبح ردي طويلا سأكتفي هنا وساضع حل يعتمد على اعادة قيمة من نوع PL TABLE باستخدام الـ COLLECTIONS

بناء الاستعلام:

select student_id, count(*)
from borrowtable
where to_char(date_of_borrow, 'MM') =to_char(sysdate, 'MM')
group by student_id
having count(*) = (select max(count(student_id)) from borrowtable where to_char(date_of_borrow, 'MM') =to_char(sysdate, 'MM') group by student_id)




create or replace package scott_pkg is
 -- Author  : SAMER
 -- Created : 16/08/2011 11:32:18 ص
 -- Purpose : agrigates all functions and procedures in one package

 -- Public type declarations
 type type_students_maxborrow_rec is record (student_id number, maxborrow number);

 type type_students_maxborrow_table is table of type_students_maxborrow_rec;
 function maxBorrowing return type_students_maxborrow_table;

end scott_pkg;


في ترويسة الباكج السابقة قمت بتعريف نوع جديد كسطر ثم استخدمته في تعريف جدول الذي سيكون قيمة الدالة المعادة إلينا.

create or replace package body scott_pkg is
function maxBorrowing return type_students_maxborrow_table
  is
  TYPE studentCurTyp IS REF CURSOR;
  student_cv studentCurTyp;
 
  v_maxborrow_table type_students_maxborrow_table;
  begin
   
open student_cv for select student_id, count(*)
                     	from borrowtable
                     	where to_char(date_of_borrow, 'MM') =to_char(sysdate, 'MM')
                     	group by student_id
                     	having count(*) = (select max(count(student_id)) from borrowtable where to_char(date_of_borrow, 'MM') =to_char(sysdate, 'MM') group by student_id);
fetch student_cv bulk collect into v_maxborrow_table;
close student_cv;
return v_maxborrow_table;
  end;
 
end scott_pkg;



الان ستعيد الدالة قيمة وحيدة وهي من نوع جدول تحوي جميع الطلاب الذين حققوا اعلى استعارات خلال الشهر الحالي.
بقي علينا أن نجرب الحصول على أرقام الطلاب وعدد الاستعارات الاعظمي من هذا الجدول

declare
 v_student_id number;
 v_borrow_max_count  number;
 v_tab scott_pkg.type_students_maxborrow_table;
begin
 v_tab := scott_pkg.maxBorrowing;
 for i in v_tab.first.. v_tab.last loop
   
dbms_output.put_line('student_id: ' || v_tab(i).student_id || ' has maximum counts of borrows: ' || v_tab(i).maxborrow  );
 end loop;

end;



ستكون النتيجة حسب البيانات التي ادخلتها أنا في الجدول هي كالتالي
student_id: 1 has maximum counts of borrows: 3
student_id: 5 has maximum counts of borrows: 3

لاحظوا اني تعمدت ان يحوي الجدول بيانات لأكثر من طالب لهم عدد استعارات أكبر من باقي الطلاب.
اخيرا في حال حدوث مشكلة ما يمكن الاستعانة بالملف المرفق
1.txt

تم تعديل بواسطة sam_t
رابط هذا التعليق
شارك

انضم إلى المناقشة

يمكنك المشاركة الآن والتسجيل لاحقاً. إذا كان لديك حساب, سجل دخولك الآن لتقوم بالمشاركة من خلال حسابك.

زائر
أضف رد على هذا الموضوع...

×   Pasted as rich text.   Paste as plain text instead

  Only 75 emoji are allowed.

×   Your link has been automatically embedded.   Display as a link instead

×   تمت استعادة المحتوى السابق الخاص بك.   مسح المحرر

×   You cannot paste images directly. Upload or insert images from URL.

جاري التحميل
×
×
  • أضف...

برجاء الإنتباه

بإستخدامك للموقع فأنت تتعهد بالموافقة على هذه البنود: سياسة الخصوصية