কেবল সুপারস্টারস নির্বাচন করুন


10

আমার কাছে দুটি সারণী রয়েছে (একটি অবিচ্ছিন্ন সূচক সহ) যা নীচের আদেশগুলি দিয়ে তৈরি করা যেতে পারে:

CREATE TABLE GroupTable
(
  GroupKey int NOT NULL PRIMARY KEY, 
  RecordCount int NOT NULL,
  GroupScore float NOT NULL
);

CREATE TABLE RecordTable
(
  RecordKey varchar(10) NOT NULL, 
  GroupKey int NOT NULL,
  PRIMARY KEY(RecordKey, GroupKey)
);

CREATE UNIQUE INDEX ixGroupRecord ON RecordTable(GroupKey, RecordKey);

প্রযুক্তিগতভাবে আমার টেবিলগুলি কিছুটা আলাদা এবং আমি কয়েকটি অন্যান্য টেবিলগুলিতে যোগ দিচ্ছি, এটি আমার পরিস্থিতির জন্য উপযুক্ত প্রক্সি।

  • আমি GroupKeysঅন্য সকলের সাবসেট নয় এমন সবগুলি নির্বাচন করতে চাই GroupKey
  • প্রদত্ত সুপারসেটের জন্য, আমি GroupScoreএর সমস্ত সাবসেট (নিজেই সহ) সর্বাধিক গ্রহন করতে চাই ।
  • উদাহরণস্বরূপ যখন একটিতে অন্যের মতো GroupKeyএকই সঠিক উপস্থিত থাকে , তারপরে কেবল তার মধ্যে একটি ধরা পড়ে (এটি কোনটি বিবেচনা করে না)।RecordKeysGroupKey(s)GroupKeys
  • কোন GroupKeyযে একই সঠিক হয়েছে RecordKeysঅন্য হিসাবে GroupKey(s)একই থাকবে GroupScore
  • অ সম্পর্কিত সম্পর্কিত GroupKeysএকই স্কোরও থাকতে পারে।

নীচে আমি যা জিজ্ঞাসা করছি তার উদাহরণ দেওয়ার জন্য একটি উদাহরণ:

              GroupTable                          RecordTable

GroupKey    RecordCount   GroupScore         RecordKey    GroupKey
------------------------------------         ---------------------
  1              3            6.2                A          1
  29             2            9.8                A          29
  95             3            6.2                A          95
  192            4            7.1                A          192
                                                 B          1
                                                 B          29
                                                 B          95
                                                 B          192
                                                 C          1
                                                 C          95
                                                 D          192
                                                 E          192

আমি আউটপুটটি নিম্নলিখিত হতে চাই:

GroupKey    RecordCount    GroupScore
-------------------------------------
  1              3             9.8
  192            4             9.8

GroupTableRecordTableপ্রায় 75M সারি রয়েছে এবং এর প্রায় 115M সারি রয়েছে; তবে যোগদানের পরে এবং WHEREভবিষ্যদ্বাণী করার পরে , একটি নির্দিষ্ট দিনে প্রায় 20k সারি থাকবে।

যদি এই প্রশ্নটি তুচ্ছ হয় তবে আমি ক্ষমা চাইছি তবে কোনও কারণে আমি সত্যিই এটির সাথে লড়াই করছি।

উত্তর:


7

আমি আউটপুটটি নিম্নলিখিত হতে চাই:

 GroupKey    RecordCount    GroupScore
 -------------------------------------
   1              3             9.8
   192            4             7.1

আপনার পছন্দের আউটপুটটি পাওয়ার জন্য ক্যারলেটেড সাবকোয়ারিগুলি ব্যবহার করা একটি উপায়।

  • উদাহরণস্বরূপ, যখন একটি গ্রুপকি অন্য গ্রুপকি (গুলি) এর মতো একই রেকর্ডকিস ধারণ করে, তখন সেই গ্রুপকিগুলির মধ্যে কেবল একটিই ধরা পড়ে (এটি কোনটি বিবেচনা করে না)।

কোনও ম্যাচ থাকাকালীন আমি সর্বনিম্ন গ্রুপকি দিয়ে গ্রুপটি ফিরিয়ে দিচ্ছি, তবে এটি যে স্বেচ্ছাচারিতায় আপনি বলছেন তাতে কিছু আসে যায় না।

পরীক্ষার ডেটা:

INSERT INTO RecordTable(RecordKey,GroupKey)
VALUES ('A',1)
     , ('A',29)
     , ('A',95)
     , ('A',192)
     , ('B',1)
     , ('B',29)
     , ('B',95)
     , ('B',192)
     , ('C',1)
     , ('C',95)
     , ('D',192)
     , ('E',192);

INSERT INTO GroupTable(GroupKey,RecordCount,GroupScore)
VALUES (1,3,6.2)     -- ABC
     , (29,2,9.8)    -- AB
     , (95,3,6.2)    -- ABC
     , (192,4,7.1);  -- ABDE
GO

প্রশ্ন:

SELECT GroupKey
     , RecordCount
     , GroupScore = ( SELECT max(GroupScore)
                      FROM GroupTable g2 
                      WHERE ( SELECT count(*)
                              FROM ( SELECT RecordKey
                                     FROM RecordTable
                                     WHERE GroupKey=g1.GroupKey
                                     UNION
                                     SELECT RecordKey
                                     FROM RecordTable
                                     WHERE GroupKey=g2.GroupKey ) z
                            )=g1.RecordCount )
FROM GroupTable g1
WHERE NOT EXISTS ( SELECT *
                   FROM GroupTable g3
                   WHERE ( SELECT count(*)
                           FROM ( SELECT RecordKey
                                  FROM RecordTable 
                                  WHERE GroupKey=g1.GroupKey 
                                  UNION
                                  SELECT RecordKey 
                                  FROM RecordTable 
                                  WHERE GroupKey=g3.GroupKey ) z )=g3.RecordCount
                         AND ( g3.RecordCount>g1.RecordCount 
                               OR ( g3.RecordCount=g1.RecordCount 
                                    AND g3.GroupKey<g1.GroupKey ) ) );
GO

SELECT এর সাবকোয়ারিটি GroupScoreকেবলমাত্র সেই গোষ্ঠীগুলির থেকে সর্বাধিক পায় যা এই ('g1') গ্রুপের সাবসেট। এটি RecordKey'g1' সেট এবং প্রতিটি 'জি 2' সেট এর 'এর ইউনিয়ন গণনা করে এটি অর্জন করে । ইউনিয়ন যদি 'g1' সেট থেকে বড় হয় তবে 'g1' সেটটির সাথে সম্পর্কিত RecordKeyনা করে 'জি 2' সেটটিতে অবশ্যই কমপক্ষে একটি থাকা উচিত RecordKey, সুতরাং 'জি 2' সেটটি উপসেট নয় এবং এর জন্য বিবেচনা করা উচিত নয় এই সারি

WHERE ধারাতে ফিল্টারিংয়ের জন্য দুটি ক্ষেত্রে বিবেচনা করা উচিত। উভয় ক্ষেত্রেই, RecordKey'জি 1' সেটটি কেবল তখনই ফিল্টার করা হয় যদি সমস্ত 'জি 1' গুলি 'জি 3' সেটটিতে উপস্থিত থাকে; এবং এই চেকটি আবার ইউনিয়ন গণনা করে অর্জন করা হয়েছে (SELECT ধারা অনুযায়ী)।

দুটি কেস হ'ল: g 'g1' সেটটির কম সংখ্যক RecordKeyগুলি রয়েছে ( g3.RecordCount>g1.RecordCount; যার ক্ষেত্রে আমরা ফিল্টার করি), এবং g 'g1' সেটটি 'g3' সেটটির অনুরূপ ( g3.RecordCount=g1.RecordCount; সেক্ষেত্রে আমরা নির্বিচারে সেটটি বেছে নিই নিম্ন GroupKey)

আউটপুট:

/*
|GroupKey|RecordCount|GroupScore|
|-------:|----------:|---------:|
|       1|          3|       9.8|
|     192|          4|       9.8|
*/

এখানে ডিবিফিডল


আমাদের সাইট ব্যবহার করে, আপনি স্বীকার করেছেন যে আপনি আমাদের কুকি নীতি এবং গোপনীয়তা নীতিটি পড়েছেন এবং বুঝতে পেরেছেন ।
Licensed under cc by-sa 3.0 with attribution required.