মাইএসকিউএল: অভ্যন্তরীণ অনুসন্ধানগুলিতে "অর্ডার বাই" দিয়ে ইউনিয়নটি অনুকূলিত করুন


9

আমি কেবলমাত্র একটি লগিং সিস্টেম সেট আপ করেছি যা একই লেআউট সহ একাধিক টেবিল সমন্বিত।

প্রতিটি ডাটা উত্সের জন্য একটি টেবিল রয়েছে।

লগ ভিউয়ারের জন্য, আমি চাই

  • ইউনিয়ন সমস্ত লগ টেবিল ,
  • অ্যাকাউন্ট দ্বারা তাদের ফিল্টার ,
  • উত্স সনাক্তকরণের জন্য ছদ্ম কলাম যুক্ত করুন ,
  • তাদের সময় অনুসারে বাছাই করুন ,
  • এবং এগুলি পৃষ্ঠাভুক্তকরণের জন্য সীমাবদ্ধ করুন

সমস্ত টেবিলগুলিতে এমন একটি ক্ষেত্র রয়েছে zeitpunktযা একটি ইনডেক্সড তারিখ / সময় কলাম।

আমার প্রথম প্রচেষ্টা ছিল:

(SELECT l.id, l.account_id, l.vnum, l.count, l.preis, l.zeitpunkt AS zeit,
 'hp' AS source FROM is_log AS l WHERE l.account_id = 730)

UNION

(SELECT l.id, l.account_id, l.vnum, l.count, l.preis, l.zeitpunkt,
 'ig' AS source FROM ig_is_log AS l WHERE l.account_id = 730)

ORDER BY zeit DESC LIMIT 10;

অপ্টিমাইজার এখানে সূচকগুলি ব্যবহার করতে পারে না কারণ উভয় টেবিলের সমস্ত সারি সাবকিউরিয়াস দ্বারা ফিরে আসে এবং এর পরে সাজানো হয় UNION

আমার কাজের ভিত্তি নিম্নলিখিত ছিল:

(SELECT l.id, l.account_id, l.vnum, l.count, l.preis, l.zeitpunkt AS zeit,
 'hp' AS source FROM is_log AS l WHERE l.account_id = 730
 ORDER BY l.zeitpunkt DESC LIMIT 10)

UNION

(SELECT l.id, l.account_id, l.vnum, l.count, l.preis, l.zeitpunkt,
 'ig' AS source FROM ig_is_log AS l WHERE l.account_id = 730
 ORDER BY l.zeitpunkt DESC LIMIT 10)

ORDER BY zeit DESC LIMIT 10;

আমি আশা করছিলাম যে কোয়েরি ইঞ্জিনটি এখানে সূচিগুলি ব্যবহার করবে যেহেতু উভয় সাবকিউরিয়াগুলি আগেই সরেজড এবং সীমাবদ্ধ হওয়া উচিত UNION, যা পরে সারিগুলিকে একত্রিত করে এবং সাজায়।

আমি সত্যিই ভেবেছিলাম এটিই হবে, তবে EXPLAINক্যোয়ারিতে চালিয়ে যাওয়া আমাকে subqueries এখনও উভয় টেবিল অনুসন্ধান করে বলে।

EXPLAINingসাবকোয়ারিগুলি নিজেরাই আমাকে পছন্দসই অপ্টিমাইজেশন দেখায় তবে UNIONingতাদের একসাথে তা হয় না।

আমি কি কিছু রেখে গেলাম?

আমি জানি যে সাবকিউয়ের ORDER BYভিতরে থাকা ধারাগুলি UNIONএকটি ছাড়া উপেক্ষা করা হয় LIMIT, তবে একটি সীমা রয়েছে।

সম্পাদনা করুন:
আসলেaccount_idশর্তছাড়াই সম্ভবত কোয়েরিও থাকবে।

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

আমাকে লগ পাঠক এবং প্রকৃত টেবিলগুলির মধ্যে এক ধরণের স্তর রাখতে হবে।

এখানে পুরো ক্যোয়ারী এবং প্রথম সাবকিউয়ের পাশাপাশি টেবিলের বিন্যাসের বিশদ বিশদভাবে কার্যকর করার পরিকল্পনা রয়েছে:

https://gist.github.com/ca8fc1093cd95b1c6fc0


1
এর জন্য সেরা সূচকটি হবে যৌগিক (account_id, zeitpunkt)। আপনার কি এমন একটি সূচক আছে? দ্বিতীয় সেরাটি হবে (আমার মনে হয়) একক হবে (zeitpunkt)- তবে যদি এটি ব্যবহার করা হয় তবে দক্ষতাটি কতটা সারি সারি account_id=730প্রদর্শিত হবে তার উপর নির্ভর করে ।
ypercubeᵀᴹ

2
আর কেন UNION DISTINCT? অতিরিক্ত বা শনাক্তকরণ কলামের কারণে ফলাফলগুলি সাবকোয়ারিগুলিতে পৃথক হবে বলে সেখানে কোনও বাছাই করতে এবং আলাদা করার দরকার নেই। ব্যবহার UNION ALL
ypercubeᵀᴹ

1
@ ইপারকিউবের পরামর্শ ছাড়াও, আমার একটি প্রশ্ন রয়েছে: sourceকলামটি যুক্ত করে , সমস্ত টেবিলে একই টেবিলে থাকা ভাল না ? এইভাবে আপনি UNIONগুলি এড়াতে এবং আপনার সমস্ত ডেটা জুড়ে সূচী (গুলি) ব্যবহার করতে পারেন।
dezso

1
@ টাইপক्यूब আসলে, অ্যাকাউন্ট_ড শর্ত ছাড়াই সম্ভবত কোয়েরিও থাকবেস্বতন্ত্র পতাকা পূর্ববর্তী চেষ্টাতে একটি বিধবা স্ত্রী এবং কারণ ফলাফল সবসময় পৃথক হবে আসলে অনর্থক এবং কারণ স্বতন্ত্র dafualt আচরণ। টেবিলগুলি ইতিমধ্যে বিদ্যমান এবং ডেটা দিয়ে পূর্ণ। যাইহোক, উত্সের উপর নির্ভর করে বিন্যাসে কিছু পরিবর্তন হতে পারে তাই আমি তাদের বিভক্ত রাখতে চাই। অতিরিক্তভাবে, লগিং ক্লায়েন্টগুলি একটি কারণে বিভিন্ন শংসাপত্র ব্যবহার করে। আমাকে লগ পাঠক এবং প্রকৃত টেবিলগুলির মধ্যে এক ধরণের স্তর রাখতে হবে।
লুকাস

ঠিক আছে, তবে পরীক্ষা UNION ALLকরে বিভিন্ন রূপায়ণ পরিকল্পনা উত্পন্ন হয় কিনা তা পরীক্ষা করে দেখুন ।
ypercubeᵀᴹ

উত্তর:


8

কৌতূহলের বাইরে, আপনি কি এই সংস্করণটি চেষ্টা করতে পারেন? সাবকিউরিগুলি পৃথকভাবে ব্যবহার করবে একই সূচকগুলি ব্যবহার করতে এটি অপ্টিমাইজারটিকে ট্রিক করতে পারে:

SELECT *
FROM
(SELECT l.id, l.account_id, l.vnum, l.count, l.preis, l.zeitpunkt AS zeit,
 'hp' AS source FROM is_log AS l WHERE l.account_id = 730
 ORDER BY l.zeitpunkt DESC LIMIT 10) 
    AS a

UNION ALL

SELECT *
FROM
(SELECT l.id, l.account_id, l.vnum, l.count, l.preis, l.zeitpunkt,
 'ig' AS source FROM ig_is_log AS l WHERE l.account_id = 730
 ORDER BY l.zeitpunkt DESC LIMIT 10)
    AS b

ORDER BY zeit DESC LIMIT 10;

আমি এখনও মনে করি যে আপনার হতে পারে সেরা সূচকটি হল যৌগিক (account_id, zeitpunkt)। এটি 10 ​​টি সারি দ্রুত উপার্জন করবে এবং কোনও কৌশল প্রয়োজন হবে না।


আপনার পরিবর্তনটি কাঙ্ক্ষিত ফলাফল আনতে পরিণত হয়েছে। ধন্যবাদ! পার্শ্ব নোট হিসাবে: এখনই আমি নিশ্চিত নই যে কোন সূচক আরও ভাল হবে। আমি উভয় ব্যবহার করতে পারে। আমি ব্যবহারকারীর সংখ্যা এবং log entries / userইচ্ছা স্কেল করতে হবে।
Lukas

আপনার যদি জিজ্ঞাসা এবং প্রশ্নগুলির বাইরে প্রয়োজন হয় তবে account_id=?দুটি রাখুন।
ypercubeᵀᴹ

@ টাইপকিউব, +1 এটি খুব চালাক এবং আমার (অনুরূপ) পরিস্থিতিতেও কাজ করেছে! আপনি কী ব্যাখ্যা করতে পারেন যে ইউনিয়নযুক্ত প্রশ্নগুলি ডামি SELECT * FROMট্রিকস মাইএসকিউএলকে কেন সূচকগুলি ব্যবহার করে মোড়ানো ?
ডিকিমিনস

@ ডকুমিনস: মাইএসকিউএল অপ্টিমাইজার খুব চালাক হয় না, সাধারণত যখন এখানে যেমন উত্সযুক্ত টেবিল থাকে তখন (SELECT ...) AS aএটি অন্যান্য উত্পন্ন টেবিলগুলি এবং তারপরে পুরো কোয়েরি থেকে আলাদাভাবে উত্পন্ন টেবিলটি মূল্যায়ন ও অনুকূলিতকরণের চেষ্টা করে।
ypercubeᵀᴹ

@ লুকাস, আসলে যেহেতু আপনার সূচিটি ব্যবহার করা হয়েছে তা নিশ্চিত করা দরকার, ব্যবহার করা / যুক্ত করা force indexআপনাকে আরও ভাল সমাধান দেবে।
পেসারিয়ার
আমাদের সাইট ব্যবহার করে, আপনি স্বীকার করেছেন যে আপনি আমাদের কুকি নীতি এবং গোপনীয়তা নীতিটি পড়েছেন এবং বুঝতে পেরেছেন ।
Licensed under cc by-sa 3.0 with attribution required.