MyoAM की तुलना में InnoDB 100x धीमे पर सरल चयन क्यों हैं?


33

मुझे काफी कष्टप्रद समस्या है। मैं अपने मुख्य डेटाबेस इंजन के रूप में INNODB का उपयोग करना चाहता हूं और MyISAM को छोड़ देना चाहता हूं क्योंकि मुझे अतिरेक के लिए गैलेरा-क्लस्टर का उपयोग करने के लिए पूर्व की आवश्यकता है।

मैंने कॉपी की गई (विवरण इस प्रकार है) newbb_postतालिका को एक नई तालिका में newbb_innopostबदल दिया और इसे इनोबीडी में बदल दिया। तालिकाएँ वर्तमान में 5,390,146प्रत्येक प्रविष्टि रखती हैं।

नए सिरे से शुरू किए गए डेटाबेस पर इन चयनों को चलाना (इसलिए इस बिंदु पर कोई कैशिंग शामिल नहीं है!) डेटाबेस निम्न परिणाम देता है (पूर्ण आउटपुट को छोड़ते हुए, कृपया ध्यान दें कि मैं डेटाबेस को परिणाम सॉर्ट करने के लिए भी नहीं कहता हूं):

सेलेक्ट पोस्ट.पोस्टिड, पोस्ट.टच फ्रॉम newbb_post एएस पोस्ट WHERE पोस्ट.थ्रेडिड = 51,0006;

।
।
| 5401593 | 0 |
| 5401634 | 0 |
+ --------- + -------- +
सेट में 62510 पंक्तियाँ (0.13 सेकंड)
सेलेक्ट पोस्ट.पोस्टिड, पोस्ट.टच फ्रॉम newbb_innopost एएस पोस्ट WHERE पोस्ट.थ्रेडिड = 51506;
।
।
| 5397410 | 0 |
| 5397883 | 0 |
+ --------- + -------- +
सेट में 62510 पंक्तियाँ (1 मिनट 22.19 सेकंड)

0.13 सेकंड से 86.19 सेकंड (!)

मैं सोच रहा हूं कि ऐसा क्यों हो रहा है। मैंने यहां कुछ जवाब पढ़े, जिसमें Stoexchange में InnoDB शामिल था और कुछ लोग बढ़ते innodb_buffer_poolरैम के आकार को 80% तक बढ़ाने का सुझाव दे रहे हैं । यह समस्या को हल नहीं करेगा, कि किसी विशेष आईडी के लिए प्रारंभिक क्वेरी में कम से कम 50 गुना अधिक समय लगेगा और पूरे वेबसर्वर को रोकना, डेटाबेस के लिए कनेक्शन और प्रश्नों को कतारबद्ध करना। बाद में कैश / बफर में किक हो सकती है, लेकिन इस डेटाबेस में 100.000 से अधिक थ्रेड हैं, इसलिए यह बहुत संभावना है कि कैश कभी भी सभी प्रासंगिक प्रश्नों को सेवा में नहीं रखेगा।

ऊपर दिए गए प्रश्न सरल हैं (कोई जोड़ नहीं), और सभी कुंजियों का उपयोग किया जाता है:

पोस्ट का चयन करें। पोस्ट पोस्ट, newbb_innopost से पोस्ट को पोस्ट करें। जहां पोस्ट के बाद हो।थ्रेडिड = 51506;
+ ------ + ------------- + ------- + ------ + ------------- ---------------------------------- + ---------- + ---- ----- + ------- + -------- + ------- +
| आईडी | select_type | तालिका | प्रकार | possible_keys | कुंजी | key_len | रेफरी | पंक्तियाँ | अतिरिक्त |
+ ------ + ------------- + ------- + ------ + ------------- ---------------------------------- + ---------- + ---- ----- + ------- + -------- + ------- +
| 1 | SIMPLE | पोस्ट | रेफरी | थ्रेडिड, थ्रेडिड .2, थ्रेडिड_विश्व_डैटलाइन | सूत्र | 4 | कॉन्स्ट | 120144 | |
+ ------ + ------------- + ------- + ------ + ------------- ---------------------------------- + ---------- + ---- ----- + ------- + -------- + ------- +

यह MyISAM-Table है:

बनाएँ तालिका `newbb_post` (
  `पोस्टिड` इंट (10) अहस्ताक्षरित नहीं पूर्ण AUTO_INCREMENT,
  `थ्रेडिड` इंट (10) अहस्ताक्षरित नॉट डीफॉल्ट '0',
  `पैरेंटिड` इंट (10) बिना नॉट डीफॉल्ट '0',
  `उपयोगकर्ता नाम` varchar (100) नहीं पूरी तरह से '',
  `userid` int (10) अहस्ताक्षरित नॉट DEFAULT '0',
  `शीर्षक` वर्चर (250) नॉट डीफॉल्ट '',
  `डेटलाइन` इंट (10) अहस्ताक्षरित नॉट डीफॉल्ट '0',
  `पगेटेक्स्ट` मध्यम,
  `allowmilie` स्मॉलिंट (6) नॉट डीफॉल्ट '0',
  `शोटिग्नेचर` स्मॉलिंट (6) नॉट डीफॉल्ट '0',
  `ipaddress` varchar (15) नॉट फुल डिफॉल्ट '',
  `iconid` smallint (5) अहस्ताक्षरित नहीं पूर्ण DEFAULT '0',
  `दृश्यमान स्मॉलिंट (6) नॉट डीफॉल्ट '0',
  `अटैचमेंट स्मॉलिंट (5) अनसॉल्व्ड नॉट नॉट डीफॉल्ट '0',
  `इन्फ्रेक्शन` स्मॉलिंट (5) अहस्ताक्षरित नॉट डीफॉल्ट '0',
  `Reportthreadid` int (10) अहस्ताक्षरित नॉट DEFAULT '0',
  `importthreadid` bigint (20) नॉट डीफॉल्ट '0',
  `importpostid` bigint (20) नॉट डीफॉल्ट '0',
  `Convert_2_utf8` int (11) पूर्ण नहीं,
  `htmlstate` enum ('off', 'on', 'on_nl2br') NOT NULL DEFAULT 'on_nl2br'
  प्राथमिक कुंजी (`पोस्टिड`),
  प्रमुख `थ्रेडिड` (` थ्रेडिड`, `यूज़रिड`),
  प्रमुख `importpost_index` (` importpostid`),
  प्रमुख `डेटलाइन` (` डेटलाइन`),
  प्रमुख `थ्रेडीड`` (` थ्रेडिड`, `दृश्यमान`,` डेटलाइन`),
  कुंजी `कनवर्ट की गई __ff8` (` कनवर्ट की गई 2_utf8`),
  प्रमुख `थ्रेडिड_विशेष_डैटलाइन` (` थ्रेडिड`, `दृश्यमान`,` डेटलाइन`, `यूज़रिड`,` पोस्टिड`),
  कुंजी `ipaddress` (` ipaddress`),
  प्रमुख `उपयोगकर्ता आईडी` (` उपयोगकर्ता नाम`, `माता-पिता`),
  कुंजी `user_date` (` उपयोगकर्ता आईडी`, `डेटलाइन`)
) इंजन = MyISAM AUTO_INCREMENT = 5402802 DEFAULT CHARSET = latin1

और यह InnoDB तालिका है (यह बिल्कुल समान है):

बनाएँ तालिका `newbb_innopost` (
  `पोस्टिड` इंट (10) अहस्ताक्षरित नहीं पूर्ण AUTO_INCREMENT,
  `थ्रेडिड` इंट (10) अहस्ताक्षरित नॉट डीफॉल्ट '0',
  `पैरेंटिड` इंट (10) बिना नॉट डीफॉल्ट '0',
  `उपयोगकर्ता नाम` varchar (100) नहीं पूरी तरह से '',
  `userid` int (10) अहस्ताक्षरित नॉट DEFAULT '0',
  `शीर्षक` वर्चर (250) नॉट डीफॉल्ट '',
  `डेटलाइन` इंट (10) अहस्ताक्षरित नॉट डीफॉल्ट '0',
  `पगेटेक्स्ट` मध्यम,
  `allowmilie` स्मॉलिंट (6) नॉट डीफॉल्ट '0',
  `शोटिग्नेचर` स्मॉलिंट (6) नॉट डीफॉल्ट '0',
  `ipaddress` varchar (15) नॉट फुल डिफॉल्ट '',
  `iconid` smallint (5) अहस्ताक्षरित नहीं पूर्ण DEFAULT '0',
  `दृश्यमान स्मॉलिंट (6) नॉट डीफॉल्ट '0',
  `अटैचमेंट स्मॉलिंट (5) अनसॉल्व्ड नॉट नॉट डीफॉल्ट '0',
  `इन्फ्रेक्शन` स्मॉलिंट (5) अहस्ताक्षरित नॉट डीफॉल्ट '0',
  `Reportthreadid` int (10) अहस्ताक्षरित नॉट DEFAULT '0',
  `importthreadid` bigint (20) नॉट डीफॉल्ट '0',
  `importpostid` bigint (20) नॉट डीफॉल्ट '0',
  `Convert_2_utf8` int (11) पूर्ण नहीं,
  `htmlstate` enum ('off', 'on', 'on_nl2br') NOT NULL DEFAULT 'on_nl2br'
  प्राथमिक कुंजी (`पोस्टिड`),
  प्रमुख `थ्रेडिड` (` थ्रेडिड`, `यूज़रिड`),
  प्रमुख `importpost_index` (` importpostid`),
  प्रमुख `डेटलाइन` (` डेटलाइन`),
  प्रमुख `थ्रेडीड`` (` थ्रेडिड`, `दृश्यमान`,` डेटलाइन`),
  कुंजी `कनवर्ट की गई __ff8` (` कनवर्ट की गई 2_utf8`),
  प्रमुख `थ्रेडिड_विशेष_डैटलाइन` (` थ्रेडिड`, `दृश्यमान`,` डेटलाइन`, `यूज़रिड`,` पोस्टिड`),
  कुंजी `ipaddress` (` ipaddress`),
  प्रमुख `उपयोगकर्ता आईडी` (` उपयोगकर्ता नाम`, `माता-पिता`),
  कुंजी `user_date` (` उपयोगकर्ता आईडी`, `डेटलाइन`)
) इंजन = इनोबीडी ऑटो_इंसीमेंट = 5402802 DEFAULT CHARSET = latin1

32GB RAM वाला सर्वर:

सर्वर संस्करण: 10.0.12-MariaDB-1 ~ भरोसेमंद- wsrep-log mariadb.org बाइनरी वितरण, wsrep_25.10.r4002

यदि आपको सभी innodb_ वैरिएबल सेटिंग की आवश्यकता है, तो मैं इस पोस्ट को संलग्न कर सकता हूं।

अद्यतन करें:

मैंने सभी सूचकांक को प्राथमिक सूचकांक से अलग कर दिया, बाद में परिणाम इस तरह से देखा:

।
।
| 5402697 | 0 |
| 5402759 | 0 |
+ --------- + -------- +
सेट में 62510 पंक्तियाँ (29.74 सेकंड)
पोस्ट का चयन करें। पोस्ट पोस्ट, newbb_innopost से पोस्ट को पोस्ट करें। जहां पोस्ट के बाद हो।थ्रेडिड = 51506;
+ ------ + ------------- + ------- + ------ + ------------- - + ------ + --------- + ------ + --------- + ------------- +
| आईडी | select_type | तालिका | प्रकार | possible_keys | कुंजी | key_len | रेफरी | पंक्तियाँ | अतिरिक्त |
+ ------ + ------------- + ------- + ------ + ------------- - + ------ + --------- + ------ + --------- + ------------- +
| 1 | SIMPLE | पोस्ट | सभी | नल | नल | नल | नल | 5909836 | जहाँ का उपयोग करना |
+ ------ + ------------- + ------- + ------ + ------------- - + ------ + --------- + ------ + --------- + ------------- +
1 पंक्ति में सेट (0.00 सेकंड)

इसके बाद मैंने सिर्फ एक इंडेक्स को वापस मिक्स, थ्रेडिड में जोड़ा, परिणाम निम्न थे:

।
।
| 5402697 | 0 |
| 5402759 | 0 |
+ --------- + -------- +
सेट में 62510 पंक्तियाँ (11.58 सेकंड)
पोस्ट का चयन करें। पोस्ट पोस्ट, newbb_innopost से पोस्ट को पोस्ट करें। जहां पोस्ट के बाद हो।थ्रेडिड = 51506;
+ ------ + ------------- + ------- + ------ + ------------- - + ---------- + --------- + ------- + -------- + ------- +
| आईडी | select_type | तालिका | प्रकार | possible_keys | कुंजी | key_len | रेफरी | पंक्तियाँ | अतिरिक्त |
+ ------ + ------------- + ------- + ------ + ------------- - + ---------- + --------- + ------- + -------- + ------- +
| 1 | SIMPLE | पोस्ट | रेफरी | सूत्र | सूत्र | 4 | कॉन्स्ट | 124622 | |
+ ------ + ------------- + ------- + ------ + ------------- - + ---------- + --------- + ------- + -------- + ------- +
1 पंक्ति में सेट (0.00 सेकंड)

अजीब बात यह है, कि किसी भी प्रासंगिक इंडेक्स के बिना, पूर्ण स्कैन में इंडेक्स (!) का उपयोग करते हुए 88 सेकंड की तुलना में केवल 29 सेकंड लगे।

केवल एक पूरी तरह से अनुरूपित सूचकांक के साथ इसे अभी भी 11 सेकंड का समय लग रहा है - अभी भी किसी भी वास्तविक दुनिया के उपयोग के लिए बहुत धीमा है।

अपडेट 2:

मैंने MySQL (5.5.38-0ubuntu0.14.04.1 (Ubuntu)) को एक ही सर्वर पर उसी हार्डवेयर कॉन्फ़िगरेशन और बिल्कुल उसी डेटाबेस / तालिकाओं के साथ सेटअप किया।

परिणाम लगभग समान हैं, पहले MyISAM तालिका:

।
।
| 5401593 | 0 |
| 5401634 | 0 |
+ --------- + -------- +
सेट में 62510 पंक्तियाँ (0.14 सेकंड)

और यह InnoDB तालिका का परिणाम है

।
।
| 5397410 | 0 |
| 5397883 | 0 |
+ --------- + -------- +
सेट में 62510 पंक्तियाँ (1 मिनट 17.63 सेकेंड)

अद्यतन 3: my.cnf की सामग्री

# MariaDB डेटाबेस सर्वर कॉन्फ़िगरेशन फ़ाइल।
#
# आप इस फ़ाइल को निम्न में से एक में कॉपी कर सकते हैं:
# - "/etc/mysql/my.cnf" वैश्विक विकल्प सेट करने के लिए,
उपयोगकर्ता-विशिष्ट विकल्प सेट करने के लिए # - "~ ~ / .my.cnf"।
# 
# एक प्रोग्राम का समर्थन करने वाले सभी लंबे विकल्पों का उपयोग कर सकता है।
# उपलब्ध विकल्पों की एक सूची प्राप्त करने के लिए --help के साथ कार्यक्रम चलाएं और साथ में
# - छाप-चूक देखने के लिए जिसे वह वास्तव में समझेगा और उपयोग करेगा।
#
# स्पष्टीकरण के लिए देखें
# http://dev.mysql.com/doc/mysql/en/server-system-variables.html

# यह सभी mysql क्लाइंट को दिया जाएगा
# यह बताया गया है कि पासवर्ड को टिक्स / कोट्स के साथ संलग्न किया जाना चाहिए
# escpatically अगर वे "#" वर्ण होते हैं ...
# सॉकेट स्थान बदलते समय /etc/mysql/debian.cnf को संपादित करना न भूलें।
[ग्राहक]
port = 3306
सॉकेट = /var/run/mysqld/mysqld.sock

# यहां कुछ विशिष्ट कार्यक्रमों के लिए प्रविष्टियां दी गई हैं
# निम्न मान मान लें कि आपके पास कम से कम 32M RAM है

# यह औपचारिक रूप से [safe_mysqld] के रूप में जाना जाता था। वर्तमान में दोनों संस्करणों को पार्स किया गया है।
[Mysqld_safe]
सॉकेट = /var/run/mysqld/mysqld.sock
अच्छा = ०

[Mysqld]
#
# * मूल सेटिंग्स
#
उपयोगकर्ता = mysql
pid-file = /var/run/mysqld/mysqld.pid
सॉकेट = /var/run/mysqld/mysqld.sock
port = 3306
अदिर = / usr
डेटादिर = / var / lib / mysql
tmpdir = / tmp
lc_messages_dir = / usr / share / mysql
lc_messages = en_US
छोड़-बाह्य-लॉकिंग
#
# स्किप-नेटवर्किंग के बजाय डिफ़ॉल्ट अब केवल सुनने के लिए है
# लोकलहोस्ट जो अधिक संगत है और कम सुरक्षित नहीं है।
बाइंड-पता = 127.0.0.1
#
# * फ़ाइन ट्यूनिंग
#
max_connections = 100
connect_timeout = 5
Wait_timeout = 600
max_allowed_packet = 16M
thread_cache_size = 128
Sort_buffer_size = 4M
बल्क_इन्टर_बफ़र_साइज़ = 16 मी
tmp_table_size = 32M
max_heap_table_size = 32M
#
# * MyISAM
#
# यह स्टार्टअप स्क्रिप्ट की जगह लेता है और यदि आवश्यक हो तो MyISAM तालिकाओं की जांच करता है
# पहली बार उन्हें छुआ गया है। त्रुटि होने पर, प्रतिलिपि बनाएं और मरम्मत का प्रयास करें।
myisam_recover = BACKUP
key_buffer_size = 128M
# ओपन-फाइल-लिमिट = 2000
table_open_cache = 400
myisam_sort_buffer_size = 512M
समवर्ती_परस्त = २
read_buffer_size = 2M
read_rnd_buffer_size = 1M
#
* * क्वेरी कैश कॉन्फ़िगरेशन
#
# कैश केवल छोटे परिणाम सेट करता है, इसलिए हम क्वेरी कैश में अधिक फिट हो सकते हैं।
query_cache_limit = 128K
query_cache_size = 64M
# अधिक गहन सेटअप लिखने के लिए, DEMAND या OFF पर सेट करें
#query_cache_type = डेमंड
#
* # लॉगिंग और प्रतिकृति
#
# क्रोनजॉब द्वारा दोनों लोकेशन को घुमाया जाता है।
# ध्यान रखें कि यह लॉग प्रकार एक प्रदर्शन हत्यारा है।
# 5.1 के रूप में आप रनटाइम पर लॉग को सक्षम कर सकते हैं!
# जेनर_लॉग_फाइल = /var/log/mysql/mysql.log
# पतवार_लोग = १
#
# त्रुटि लॉगिंग /etc/mysql/conf.d/mysqld_safe_syslog.cnf के कारण syslog में जाती है।
#
# हम नेटवर्क त्रुटियों और इस तरह के बारे में जानना चाहते हैं
log_warnings = 2
#
# विशेष रूप से लंबी अवधि वाले प्रश्नों को देखने के लिए धीमी क्वेरी लॉग को सक्षम करें
#slow_query_log [= {0 | 1}]
slow_query_log_file = /var/log/mysql/mariadb-slow.log
long_query_time = 10
#log_slow_rate_limit = 1000
log_slow_verbosity = query_plan

# लॉग-प्रश्नों-नहीं-का उपयोग कर-अनुक्रमित
#log_slow_admin_statements
#
# बैकअप लॉग या प्रतिकृति के लिए पुन: उपयोग करना आसान हो सकता है।
# नोट: यदि आप एक प्रतिकृति दास की स्थापना कर रहे हैं, तो README.Debian के बारे में देखें
# अन्य सेटिंग्स आपको बदलने की आवश्यकता हो सकती है।
# सर्वर-आईडी = 1
#report_host = मास्टर 1
# आटो_संकल्प_संकल्प = 2
# आटो_सिनारमेंट_ऑफसेट = 1
log_bin = / var / log / mysql / mariadb-bin
log_bin_index = /var/log/mysql/mariadb-bin.index
# प्रदर्शन के लिए फैब नहीं बल्कि सुरक्षित
#sync_binlog = 1
expire_logs_days = 10
max_binlog_size = 100M
# गुलाम
#relay_log = / var / log / mysql / रिले-बिन
#relay_log_index = /var/log/mysql/relay-bin.index
#relay_log_info_file =/var/log/mysql/relay-bin.info
#log_slave_updates
#सिफ़ पढ़िये
#
# यदि अनुप्रयोग इसका समर्थन करते हैं, तो यह सख्त sql_mode कुछ को रोकता है
# गलत तारीखें डालने जैसी गलतियां आदि।
#sql_mode = NO_ENGINE_SUBSTITUTION, TRADITIONAL
#
* * InnoDB
#
# InnoDB डिफ़ॉल्ट रूप से / var / lib / mysql / में 10MB डेटाफाइल के साथ सक्षम है।
# अधिक InnoDB संबंधित विकल्पों के लिए मैनुअल पढ़ें। वहां कई हैं!
default_storage_engine = InnoDB
# आप केवल लॉग फ़ाइल का आकार नहीं बदल सकते हैं, विशेष प्रक्रिया की आवश्यकता है
#innodb_log_file_size = 50M
innodb_buffer_pool_size = 20G
innodb_log_buffer_size = 8M
innodb_file_per_table = 1
innodb_open_files = 400
innodb_io_capacity = 400
innodb_flush_method = O_DIRECT
#
# * सुरक्षा विशेषताएं
#
# अगर आप चुरोट चाहते हैं, तो मैनुअल भी पढ़ें!
# चुरोट = / var / lib / mysql /
#
# एसएसएल प्रमाणपत्र बनाने के लिए मैं ओपनएसएसएल जीयूआई "टिनिआ" की सिफारिश करता हूं।
#
# ssl-ca = / etc / mysql / cacert.pem
# एसएसएल-सर्टिफिकेट = / etc / mysql / server-cert.pem
# ssl-key = / etc / mysql / server-key.pem



[Mysqldump]
शीघ्र
बोली-नाम
max_allowed_packet = 16M

[माई एसक्यूएल]
# no-auto-rehash # mysql की तेज शुरुआत लेकिन कोई टैब पूर्णता नहीं

[Isamchk]
key_buffer = 16M

#
* * महत्वपूर्ण: अतिरिक्त सेटिंग्स जो इस फ़ाइल से ओवरराइड कर सकती हैं!
# फाइलें '.cnf' के साथ समाप्त होनी चाहिए, अन्यथा उन्हें नजरअंदाज कर दिया जाएगा।
#
शामिल किया गया /etc/mysql/conf.d/

और इनो चर की सामग्री:

मारियाबडी [(कोई नहीं)]> वार वारब्लस ''%% 'को पसंद करता है;
+ ------------------------------------------- + ----- ------------------- +
| चर_नाम | मान |
+ ------------------------------------------- + ----- ------------------- +
| innodb_adaptive_flushing | पर |
| innodb_adaptive_flushing_lwm | 10 |
| innodb_adaptive_hash_index | पर |
| innodb_adaptive_hash_index_partitions | 1 |
| innodb_adaptive_max_sleep_delay | 150000 |
| innodb_additional_mem_pool_size | 8388608 |
| innodb_api_bk_commit_interval | 5 |
| innodb_api_disable_rowlock | उतर |
| innodb_api_enable_binlog | उतर |
| innodb_api_enable_mdl | उतर |
| innodb_api_trx_level | 0 |
| innodb_autoextend_increment | 64 |
| innodb_autoinc_lock_mode | 1 |
| innodb_buffer_pool_dump_at_shutdown | उतर |
| innodb_buffer_pool_dump_now | उतर |
| innodb_buffer_pool_filename | ib_buffer_pool |
| innodb_buffer_pool_instances | 8 |
| innodb_buffer_pool_load_abort | उतर |
| innodb_buffer_pool_load_at_startup | उतर |
| innodb_buffer_pool_load_now | उतर |
| innodb_buffer_pool_populate | उतर |
| innodb_buffer_pool_size | 21474836480 |
| innodb_change_buffer_max_size | 25 |
| innodb_change_buffering | सभी |
| innodb_checksum_algorithm | निर्दोष |
| innodb_checksums | पर |
| innodb_cleaner_lsn_age_factor | high_checkpoint |
| innodb_cmp_per_index_enabled | उतर |
| innodb_commit_concurrency | 0 |
| innodb_compression_failure_threshold_pct | 5 |
| innodb_compression_level | 6 |
| innodb_compression_pad_pct_max | 50 |
| innodb_concurrency_ticket | 5000 |
| innodb_corrupt_table_action | मुखर |
| innodb_data_file_path | ibdata1: 12M: autoextend |
| innodb_data_home_dir | |
| innodb_disable_sort_file_cache | उतर |
| innodb_doublewrite | पर |
| innodb_empty_free_list_algorithm | बैकऑफ़ |
| innodb_fake_changes | उतर |
| innodb_fast_shutdown | 1 |
| innodb_file_format | एंटीलोप |
| innodb_file_format_check | पर |
| innodb_file_format_max | एंटीलोप |
| innodb_file_per_table | पर |
| innodb_flush_log_at_timeout | 1 |
| innodb_flush_log_at_trx_commit | 1 |
| innodb_flush_method | O_DIRECT |
| innodb_flush_neighbors | 1 |
| innodb_flushing_avg_loops | 30 |
| innodb_force_load_corrupted | उतर |
| innodb_force_recovery | 0 |
| innodb_foreground_preflush | घातांक_बैकऑफ़ |
| innodb_ft_aux_table | |
| innodb_ft_cache_size | 8000000 |
| innodb_ft_enable_diag_print | उतर |
| innodb_ft_enable_stopword | पर |
| innodb_ft_max_token_size | 84 |
| innodb_ft_min_token_size | 3 |
| innodb_ft_num_word_optimize | 2000 |
| innodb_ft_result_cache_limit | 2000000000 |
| innodb_ft_server_stopword_table | |
| innodb_ft_sort_pll_degree | 2 |
| innodb_ft_total_cache_size | 640000000 |
| innodb_ft_user_stopword_table | |
| innodb_io_capacity | 400 |
| innodb_io_capacity_max | 2000 |
| innodb_kill_idle_transaction | 0 |
| innodb_large_prefix | उतर |
| innodb_lock_wait_timeout | 50 |
| innodb_locking_fake_changes | पर |
| innodb_locks_unsafe_for_binlog | उतर |
| innodb_log_arch_dir | ./ |
| innodb_log_arch_expire_sec | 0 |
| innodb_log_archive | उतर |
| innodb_log_block_size | 512 |
| innodb_log_buffer_size | 8388608 |
| innodb_log_checksum_algorithm | निर्दोष |
| innodb_log_compressed_pages | पर |
| innodb_log_file_size | 50331648 |
| innodb_log_files_in_group | 2 |
| innodb_log_group_home_dir | ./ |
| innodb_lru_scan_depth | 1024 |
| innodb_max_bitmap_file_size | 104857600 |
| innodb_max_changed_pages | 1000000 |
| innodb_max_dirty_pages_pct | 75 |
| innodb_max_dirty_pages_pct_lwm | 0 |
| innodb_max_purge_lag | 0 |
| innodb_max_purge_lag_delay | 0 |
| innodb_mirrored_log_groups | 1 |
| innodb_monitor_disable | |
| innodb_monitor_enable | |
| innodb_monitor_reset | |
| innodb_monitor_reset_all | |
| innodb_old_blocks_pct | 37 |
| innodb_old_blocks_time | 1000 |
| innodb_online_alter_log_max_size | 134217728 |
| innodb_open_files | 400 |
| innodb_optimize_fulltext_only | उतर |
| innodb_page_size | 16384 |
| innodb_print_all_deadlocks | उतर |
| innodb_purge_batch_size | 300 |
| innodb_purge_threads | 1 |
| innodb_random_read_ahead | उतर |
| innodb_read_ahead_threshold | 56 |
| innodb_read_io_threads | 4 |
| innodb_read_only | उतर |
| innodb_replication_delay | 0 |
| innodb_rollback_on_timeout | उतर |
| innodb_rollback_seolution | 128 |
| innodb_sched_priority_cleaner | 19 |
| innodb_show_locks_held | 10 |
| innodb_show_verbose_locks | 0 |
| innodb_sort_buffer_size | 1048576 |
| innodb_spin_wait_delay | 6 |
| innodb_stats_auto_recalc | पर |
| innodb_stats_method | nulls_equal |
| innodb_stats_on_metadata | उतर |
| innodb_stats_persistent | पर |
| innodb_stats_persistent_sample_pages | 20 |
| innodb_stats_sample_pages | 8 |
| innodb_stats_transient_sample_pages | 8 |
| innodb_status_output | उतर |
| innodb_status_output_locks | उतर |
| innodb_strict_mode | उतर |
| innodb_support_xa | पर |
| innodb_sync_array_size | 1 |
| innodb_sync_spin_loops | 30 |
| innodb_table_locks | पर |
| innodb_thread_concurrency | 0 |
| innodb_thread_sleep_delay | 10000 |
| innodb_track_changed_pages | उतर |
| innodb_undo_directory | । |
| innodb_undo_logs | 128 |
| innodb_undo_tablespaces | 0 |
| innodb_use_atomic_writes | उतर |
| innodb_use_fallocate | उतर |
| innodb_use_global_flush_log_at_trx_commit | पर |
| innodb_use_native_aio | पर |
| innodb_use_stacktrace | उतर |
| innodb_use_sys_malloc | पर |
| innodb_version | 5.6.17-65.0 |
| innodb_write_io_threads | 4 |
+ ------------------------------------------- + ----- ------------------- +
सेट में 143 पंक्तियाँ (0.02 सेकंड)

मशीन के कोर की संख्या 8 है, यह ए है

Intel(R) Xeon(R) CPU E3-1246 v3 @ 3.50GHz के रूप में /proc/cpuinfo

एक अंतिम नोट: रॉलेंडोएमवाईएसडीएलडीबीए द्वारा सुझाए गए सूचकांक के साथ प्रश्नों को चलाएं, और प्रश्नों में से प्रत्येक के बारे में 11-20 अंक थे। मैं यह बताना चाहता हूं कि यह मेरे लिए महत्वपूर्ण है (यह बुलेटिन बोर्ड की मुख्य तालिका है) कि एक थ्रेडिड के बारे में पहली क्वेरी एक सेकंड से भी कम समय में लौटती है, क्योंकि 60.000 से अधिक थ्रेड्स और google-bots लगातार क्रॉल होते हैं ये सूत्र।


टिप्पणियाँ विस्तारित चर्चा के लिए नहीं हैं; इस वार्तालाप को बातचीत में स्थानांतरित कर दिया गया है ।
पॉल व्हाइट GoFundMonica कहते

जवाबों:


24

तुम्हारे सवाल

SELECT post.postid, post.attach FROM newbb_innopost AS post WHERE post.threadid = 51506;

पहली नज़र में, उस क्वेरी को तालिका के 1.1597% (5390146 में से 62510) को छूना चाहिए। इसे तेजी से थ्रेडिड 51506 का महत्वपूर्ण वितरण दिया जाना चाहिए।

वास्तविकता की जांच

कोई फर्क नहीं पड़ता कि आप MySQL (Oracle, Percona, MariaDB) का कौन सा संस्करण उपयोग करते हैं, उनमें से कोई भी एक दुश्मन से नहीं लड़ सकता है, जो सभी के लिए समान है: इनोबीडी आर्किटेक्चर।

InnoDB वास्तुकला

अनुकूलित सूचकांक

कृपया ध्यान रखें कि प्रत्येक थ्रेडिड प्रविष्टि में एक प्राथमिक कुंजी संलग्न है। इसका मतलब है कि जब आप इंडेक्स से पढ़ते हैं, तो उसे ClusteredIndex (आंतरिक रूप से नामित gen_clust_index) के भीतर एक प्राथमिक कुंजी लुकअप करना चाहिए । ClusteredIndex में, प्रत्येक InnoDB पेज में डेटा और PRIMARY KEY दोनों इंडेक्स जानकारी होती है। अधिक जानकारी के लिए मेरी पोस्ट बेस्ट ऑफ मायसम और इनोबीडी देखें ।

आधुनिक सूचकांक

आपके पास तालिका में बहुत अधिक अव्यवस्था है क्योंकि कुछ अनुक्रमित में एक ही प्रमुख स्तंभ हैं। MySQL और InnoDB को आवश्यक BTREE नोड्स को प्राप्त करने के लिए सूचकांक अव्यवस्था के माध्यम से नेविगेट करना होगा। आपको निम्न को चलाकर उस अव्यवस्था को कम करना चाहिए:

ALTER TABLE newbb_innopost
    DROP INDEX threadid,
    DROP INDEX threadid_2,
    DROP INDEX threadid_visible_dateline,
    ADD INDEX threadid_visible_dateline_index (`threadid`,`visible`,`dateline`,`userid`)
;

इन इंडेक्स को क्यों स्ट्रिप किया जाए?

  • पहले तीन सूचकांक थ्रेडिड से शुरू होते हैं
  • threadid_2और threadid_visible_datelineउसी तीन कॉलम के साथ शुरू करें
  • threadid_visible_dateline यह प्राथमिक कुंजी है और यह एम्बेडेड है क्योंकि यह पोस्टिड की जरूरत नहीं है

बफ़र कोचिंग

InnoDB बफर पूल डेटा और इंडेक्स पेजों को कैश करता है। MyISAM केवल इंडेक्स पेजों को कैश करता है।

सिर्फ इस क्षेत्र में, MyISAM समय कैशिंग डेटा बर्बाद नहीं करता है। ऐसा इसलिए है क्योंकि यह डेटा कैश करने के लिए डिज़ाइन नहीं किया गया है। InnoDB हर डेटा पेज और इंडेक्स पेज (और उसकी दादी) को छूता है। यदि आपका InnoDB बफर पूल बहुत छोटा है, तो आप पृष्ठों को कैशिंग कर सकते हैं, पृष्ठों को अमान्य कर सकते हैं, और सभी पृष्ठों को एक क्वेरी में हटा सकते हैं।

टेबल के बारे में

आप विचार करके importthreadidऔर पंक्ति से कुछ स्थान की दाढ़ी बना सकते हैं importpostid। आप उन्हें बड़े के रूप में है। वे प्रति पंक्ति ClusteredIndex में 16 बाइट्स लेते हैं।

आपको इसे चलाना चाहिए

SELECT importthreadid,importpostid FROM newbb_innopost PROCEDURE ANALYSE();

यह अनुशंसा करेगा कि दिए गए डेटासेट के लिए ये कॉलम किस प्रकार के होने चाहिए।

निष्कर्ष

MyISAM में इनोबीडी की तुलना में काफी कम है, खासकर कैशिंग के क्षेत्र में।

जब आपने RAM ( 32GB) और MySQL ( Server version: 10.0.12-MariaDB-1~trusty-wsrep-log mariadb.org binary distribution, wsrep_25.10.r4002) के संस्करण का खुलासा किया, तो इस पहेली के अन्य टुकड़े अभी भी हैं जिनका आपने खुलासा नहीं किया है

  • InnoDB सेटिंग्स
  • कोर की संख्या
  • से अन्य सेटिंग्स my.cnf

यदि आप इन बातों को प्रश्न में जोड़ सकते हैं, तो मैं और विस्तृत कर सकता हूं।

UPDATE 2014-08-28 11:27 EDT

आपको थ्रेडिंग बढ़ानी चाहिए

innodb_read_io_threads = 64
innodb_write_io_threads = 16
innodb_log_buffer_size = 256M

मैं क्वेरी कैश को अक्षम करने पर विचार करूंगा (मेरी हाल की पोस्ट देखें क्यों query_cache_type को MySQL 5.6 से डिफ़ॉल्ट रूप से अक्षम किया गया है? )

query_cache_size = 0

मैं बफ़र पूल को संरक्षित करूंगा

innodb_buffer_pool_dump_at_shutdown=1
innodb_buffer_pool_load_at_startup=1

शुद्ध धागे बढ़ाएं (यदि आप कई टेबल पर डीएमएल करते हैं)

innodb_purge_threads = 4

कोशिश तो करो !!!


मुझे पता है कि InnoDB का मतलब शुद्ध गति परीक्षण में धीमा होना है, लेकिन इस हद तक? मैंने पढ़ा है कि MySQL टीम इस अंतर को बंद करने के लिए कड़ी मेहनत कर रही है। हम अभी भी ~ 100 गुना वृद्धि के साथ काम कर रहे हैं! प्रश्न - क्या आप कह रहे हैं कि इस प्रकृति के प्रश्नों को "प्रत्यक्ष" गैर-क्लस्टर बी-ट्री इंडेक्स (यानी पीके डेटा शामिल नहीं है) के साथ बेहतर तरीके से परोसा जाएगा? यदि हां, तो इसे लागू क्यों नहीं किया जा रहा है? ओपी को जिस कार्यक्षमता की आवश्यकता होती है वह निश्चित रूप से सीमांत उपयोग का मामला नहीं है।
22

क्या आप उस चित्र के पूर्ण आकार संस्करण के लिए एक लिंक जोड़ सकते हैं? कुछ हिस्सों को पढ़ना मुश्किल है :-)
पानी वाला

@RolandMySQLDBA जानकारी के लिए धन्यवाद - मुझे आशा है कि आप सुझाव नहीं दे रहे हैं कि InnoDB के लिए एक 100x मंदी "सामान्य" है ... मैं 2x या 3x के साथ रह सकता था, लेकिन 100x बस बहुत अधिक है। अनुरोध के अनुसार मैंने अपने प्रश्न में अनुपलब्ध जानकारी जोड़ी है :) अब तक के स्पष्टीकरण के लिए धन्यवाद! मशीन के कोर की संख्या 8. है
जॉलीगर

2
@ वाटरली यहाँ फुल साइज़ पिक्चर है: scribd.com/doc/31337494/XtraDB-InnoDB-internals-in-drawing
RolandoMySQLDBA

1
आपकी मदद के लिए बहुत बहुत धन्यवाद @RolandoMySQLDBA, दुर्भाग्य से यहां तक ​​कि उन आखिरी ट्वीक्स ने भी मदद नहीं की, और InnoDB को पूरा करने में लगभग 11-20 सेकंड लगते हैं। मैंने आपके उत्तर के आधार पर कुछ करने की कोशिश की - सभी अनुक्रमों को छोड़ने, और एक कवरिंग इंडेक्स बनाने के लिए। जिससे काफी मदद मिली है। अनुक्रमणिका के आपके स्पष्टीकरण के बिना मुझे यह समाधान नहीं मिला। अपने उत्तर की जाँच करने के लिए और एक उत्तर लिखने के लिए खुद को समझाते हुए कि मैंने क्या किया :)
जॉलीगर

7

@RolandMySQLDBA ने सवाल का जवाब देने के लिए सही संकेत दिया है। समस्या क्वेरी में झूठ लगती है और यह कि परिणाम वापस दिए जाने के लिए, उन क्षेत्रों में से प्रत्येक को पढ़ना होगा (किसी भी तरह डेटाबेस से)।

मैंने सभी अनुक्रमों को छोड़ दिया PRIMARY KEY, लेकिन इस नए सूचकांक को सम्मिलित किया:

ALTER TABLE newbb_innopost ADD INDEX threadid_visible_dateline_index (threadid,visible,dateline,userid,attach,ipaddress);

यह लिंक बताता है कि यहां क्या होता है ( इंडेक्स को कवर करते हुए ): क्वेरी के क्वेरी किए गए फ़ील्ड जो postid,attachअब कुंजी से ही निकाले जा सकते हैं। यह वास्तविक डेटा की जांच करने और हार्ड डिस्क पर I / O का उपयोग करने से बचाता है।

सभी प्रश्न अब 0.00 सेकंड के साथ चलते हैं .. :)

आपकी मदद के लिए बहुत बहुत धन्यवाद।

संपादित करें : वास्तविक अंतर्निहित समस्या हल नहीं हुई है, मैंने इस तकनीक के साथ इसे दरकिनार कर दिया है। इस क्षेत्र में InnoDB को कुछ गंभीर फिक्सिंग की आवश्यकता है।


मैं एक ही मुद्दे का सामना कर रहा हूँ। myisma query में 0.01 सेकंड लगते हैं जबकि innodb में 60 सेकंड लगते हैं, अपने सुझावों को आज़माएं।
अंब

@AMB - 0.01 के दशक कैश की तरह बदबू आ रही है; इसे फिर से समय के साथ SQL_NO_CACHE
रिक जेम्स

0

आपके क्वेरी और टेबल दोनों के आधार पर ऐसा लगता है कि आप टाइम-सीरीज़ टेबल से सेलेकग डेटा हैं। जैसे, यह हो सकता है कि क्वेरी समय धीमा है क्योंकि आप एक साथ सम्मिलित कर रहे हैं?

अगर वे दो चीजें सच हैं, तो क्या मैं एक विकल्प के रूप में स्केलबीडी में देखने का सुझाव दे सकता हूं? आप अभी भी मारियाडीबी पर होंगे, बस (शायद) अधिक उपयुक्त इंजन।

http://www.scaledb.com - मुखपृष्ठ http://www.scaledb.com/download-form.php - हमारा उत्पाद


2
आपको जोड़ना चाहिए कि प्रमुख संस्करण मुक्त नहीं है।
ypercube y

0

दोनों इंजन क्वेरी को बहुत तेज़ी से चलाएंगे

INDEX(threadid, attach, postid)

ऐसा इसलिए है क्योंकि यह एक "कवरिंग" सूचकांक होगा, और लगभग उसी तरह से काम करेगा (सूचकांक BTree का उपयोग करके)।

इसके अलावा, मैं कहेंगे कि यह संभव नहीं है या तो एक "ठंड" सर्वर पर इंजन:

62510 rows in set (0.13 sec)

कृपया SQL_NO_CACHEसमय-समय पर चलने का उपयोग करें - हम निष्कर्ष को प्रदूषित करने के लिए क्वेरी कैश नहीं चाहते हैं।

एक और तेजी से दृष्टिकोण (आई / ओ कैशिंग के बावजूद):

InnoDB का उपयोग करें, और से परिवर्तित PRIMARY KEY (postid)करें

PRIMARY KEY(threadid, postid),
INDEX(postid)

कारण यह है कि इससे सभी प्रासंगिक पंक्तियां समीप हो जाएंगी, जिससे I / O, आदि की कम आवश्यकता होती INDEX(postid)है AUTO_INCREMENT। कैविएट: यह सभी माध्यमिक कुंजी के साथ गड़बड़ करता है - कुछ तेज होगा, कुछ धीमा होगा।


0

हालांकि सीधे @jollyroger के लिए लागू नहीं है क्योंकि उसके पास पहले से ही सही सेटिंग है, लेकिन मुझे एक बड़ी सुधार मिली, जिससे innodb_buffer_pool_sizeमेरी रैम का 70% हिस्सा बदल गया क्योंकि मुझे बताया गया कि इनोडब की तुलना में मायसम क्यों धीमा है

पहले MyISAMधीमा था, लेकिन मजाक। फिर InnoDBचीजों को खराब कर दिया, इस सवाल में 100x धीमे के समान और सेटिंग बदलने के बाद InnoDB10x तेज हो गया MyISAM

मेरी डिफ़ॉल्ट सेटिंग 8MB पर थी जो बहुत कम है।

हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.