حدد أقصى درجات مجمعة حسب التاريخ، وعرض DateTime الكامل

StackOverflow https://stackoverflow.com/questions/1452839

سؤال

Gday، لدي جدول يعرض سلسلة من الدرجات وقضاء هذه الدرجات التي حدثت تلك النتائج. أرغب في تحديد الحد الأقصى لهذه الدرجات لكل يوم، ولكن عرض DateTime الذي حدث فيه النتيجة.

أنا أستخدم قاعدة بيانات Oracle (10G) ويتم تنظيم الجدول مثل ذلك:

 النتيجة ScoredateTime (عدد صحيح) --------------------------------------- 01-Jan-09 00 : 10: 00 10 01 01-يناير 09 01:00 11 01 01-يناير 09 04:00 ...

أود أن أكون قادرا على تقديم النتائج التي تحدث أعلاه:

 01-يناير 09 01:00:00 11

هذا الاستعلام التالي يحصل لي في منتصف الوقت هناك .. ولكن ليس على طول الطريق.

select 
   trunc(t.scoredatetime), max(t.score)
from 
   mytable t
group by
   trunc(t.scoredatetime)

لا أستطيع الانضمام إلى النتيجة فقط لأن نفس النتيجة المرتفعة قد تحقق عدة مرات طوال اليوم.

انا اقدر مساعدتك!

سيمون إدواردز

هل كانت مفيدة؟

المحلول

with mytableRanked(d,scoredatetime,score,rk) as (
  select
    scoredatetime,
    score,
    row_number() over (
      partition by trunc(scoredatetime)
      order by score desc, scoredatetime desc
    )
  from mytable
)
  select
    scoredatetime,
    score
  from mytableRanked    
  where rk = 1
  order by date desc

في حالة وجود درجات عالية متعددة في غضون يوم واحد، ترجع هذا الصف المقابل للآخر حدث آخر في اليوم. إذا كنت ترغب في رؤية كل أعلى درجات في يوم واحد، فقم بإزالة DescorateTime Desc من الطلب عن طريق المواصفات في نافذة Row_Number.

بدلا من ذلك، يمكنك القيام بذلك (سوف يسرد علاقات النتيجة العالية للتاريخ):

select
  scoredatetime,
  score
from mytable
where not exists (
  select *
  from mytable as M2
  where trunc(M2.scoredatetime) = trunc(mytable.scoredatetime)
  and M2.score > mytable.scoredatetime
)
order by scoredatetime desc

نصائح أخرى

بادئ ذي بدء، لم تحدد بعد ما يجب أن يحدث إذا احتواء صفين أو أكثر في نفس اليوم درجة عالية متساوية.

إجابات محتملة لهذا السؤال:

1) ما عليك سوى اختيار أحد Scoredateme's، لا يهم أي واحد

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

SQL> create table mytable (scoredatetime,score)
  2  as
  3  select to_date('01-jan-2009 00:10:00','dd-mon-yyyy hh24:mi:ss'), 10 from dual union all
  4  select to_date('01-jan-2009 01:00:00','dd-mon-yyyy hh24:mi:ss'), 11 from dual union all
  5  select to_date('01-jan-2009 04:00:00','dd-mon-yyyy hh24:mi:ss'), 9 from dual union all
  6  select to_date('02-jan-2009 00:10:00','dd-mon-yyyy hh24:mi:ss'), 1 from dual union all
  7  select to_date('02-jan-2009 01:00:00','dd-mon-yyyy hh24:mi:ss'), 1 from dual union all
  8  select to_date('02-jan-2009 04:00:00','dd-mon-yyyy hh24:mi:ss'), 0 from dual
  9  /

Table created.

SQL> select max(scoredatetime) keep (dense_rank last order by score) scoredatetime
  2       , max(score)
  3    from mytable
  4   group by trunc(scoredatetime,'dd')
  5  /

SCOREDATETIME       MAX(SCORE)
------------------- ----------
01-01-2009 01:00:00         11
02-01-2009 01:00:00          1

2 rows selected.

2) حدد جميع السجلات بأقصى درجات.

في هذه الحالة، تحتاج إلى تحليلات مع وظيفة رتبة أو dense_rank. مثال:

SQL> select scoredatetime
  2       , score
  3    from ( select scoredatetime
  4                , score
  5                , rank() over (partition by trunc(scoredatetime,'dd') order by score desc) rnk
  6             from mytable
  7         )
  8   where rnk = 1
  9  /

SCOREDATETIME            SCORE
------------------- ----------
01-01-2009 01:00:00         11
02-01-2009 00:10:00          1
02-01-2009 01:00:00          1

3 rows selected.

التحيات، روب.

قد تحتاج إلى بيانات اختيارين لسحب هذا: أول من جمع التاريخ المقتطع والدرجة القصوى المرتبطة بحد أقصى، والثاني لسحب قيم البيانات الفعلية المرتبطة بالنتيجة.

يحاول:

SELECT T.ScoreDateTime, T.Score
FROM
(
 SELECT
    TRUNC(T.ScoreDateTime) ScoreDate, MAX(T.score) BestScore
 FROM 
    MyTable T
 GROUP BY 
    TRUNC(T.ScoreDateTime)
) ByDate
INNER JOIN MyTable T 
    ON TRUNC(T.ScoreDateTime) = ByDate.ScoreDate and T.Score = ByDate.BestScore
ORDER BY T.ScoreDateTime DESC

هذا سوف يسحب أفضل علاقات النتيجة أيضا.

للحصول على إصدار يختار فقط النتيجة المرتفعة التي تم نشرها مؤخرا لكل يوم:

SELECT T.ScoreDateTime, T.Score
FROM
(
 SELECT
    TRUNC(T.ScoreDateTime) ScoreDate, 
    MAX(T.score) BestScore, 
    MAX(T.ScoreDateTime) BestScoreTime
 FROM 
    MyTable T
 GROUP BY 
    TRUNC(T.ScoreDateTime)
) ByDate
INNER JOIN MyTable T 
    ON T.ScoreDateTime = ByDate.BestScoreTime and T.Score = ByDate.BestScore
ORDER BY T.ScoreDateTime DESC

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

مرخصة بموجب: CC-BY-SA مع الإسناد
لا تنتمي إلى StackOverflow
scroll top