क्या डोम में तत्वों की हैश-टेबल है जिनकी चाबियाँ तत्व हैं Iids?
मैं जानना चाहता हूं कि document.getElementById
हैश तालिका देखता है या पूरे पेड़ को पार करता है।
क्या यह व्यवहार ब्राउज़र भर में अलग है?जावास्क्रिप्ट getElementById लुकअप - हैश मानचित्र या रिकर्सिव पेड़ ट्रैवर्सल?
उत्तर
कार्यान्वयन जो भी उन्हें पसंद है, करने के लिए स्वतंत्र हैं, लेकिन id
को एक अद्वितीय मूल्य के रूप में परिभाषित किया गया है, यह एक हैश मानचित्र या ट्रैवर्सल के बजाय समान लुकअप तंत्र का उपयोग करने के लिए समझदार प्रतीत होता है। बाहर से समझदार प्रतीत होता है, हालांकि, जब आप कई जटिल (कभी-कभी विरोधाभासी) अनिवार्यताओं के साथ एक जटिल वेब ब्राउज़र बनाने की नलसाजी में नहीं आते हैं।
मैंने एक आसान किया लेकिन बहुत सरल परीक्षण (उत्तर के अंत में पृष्ठ देखें)। यह बहुत सरल नहीं है क्योंकि हम नहीं जानते कि ब्राउज़र पिछले परिणामों को कैश नहीं करते हैं।
क्रोम 4.1.249.1059 रिपोर्ट:
ID: 0.0082ms per lookup
Tag: 0.0249ms per lookup
तो, नाटकीय रूप से तेजी से टैग नाम से आईडी के आधार पर।
IE7 रिपोर्ट:
ID: 2.4438ms per lookup
Tag: 0.0437ms per lookup
आईडी से
तो नाटकीय रूप से तेजी से टैग नाम से (लेकिन याद IE7 एक broken concept of getElementById
है, इस IE8 में तय हो गई है)।
IE8 (एक अलग मशीन पर, निरपेक्षता की तुलना नहीं करते, हम ब्राउज़र का परीक्षण भीतर डिफ पर देख रहे हैं) रिपोर्ट:
ID: 1.1335ms per lookup
Tag: 0.0287ms per lookup
तो के बारे में IE7 के रूप में ही।
फ़ायरफ़ॉक्स 3.6।3 रिपोर्ट:
ID: 0.0042ms per lookup
Tag: 0.006ms per lookup
तो यह है कि ज्यादा परवाह नहीं करता है (कई बार अनुरोध पर; फिर, यह कैशिंग जा सकता है)।
ओपेरा 10.5.1 रिपोर्ट:
ID: 0.006ms per lookup
Tag: 1.467ms per lookup
नाटकीय रूप से तेजी से
टैग नाम से आईडी के आधार पर।
उन परिणामों का बनाएं जो आप करेंगे। वास्तव में तंत्र का अनुमान लगाने के लिए एक और जटिल परीक्षण मामले की आवश्यकता होगी। बेशक, कम से कम दो मामलों में (फ़ायरफ़ॉक्स और क्रोम), हम स्रोत पर जा सकते हैं। points usWebKit और Firefox कार्यान्वयन के लिए कृपया (और इसे देखकर, कैशिंग के बारे में मेरा संदेह on the money हो सकता है)।
टेस्ट पेज:
<!DOCTYPE HTML>
<html>
<head>
<meta http-equiv="Content-type" content="text/html;charset=UTF-8">
<title>Test Page</title>
<style type='text/css'>
body {
font-family: sans-serif;
}
#log p {
margin: 0;
padding: 0;
}
</style>
<script type='text/javascript'>
window.onload = pageInit;
function pageInit() {
document.getElementById('btnGo').onclick = btnGoClick;
}
function btnGoClick() {
log("Testing...");
setTimeout(run, 0);
}
function run() {
var count, time;
try {
// Warm up
testid(10);
testtag(10);
// Test
count = 10000
time = testid(count);
log("ID: " + (time/count) + "ms per lookup");
time = testtag(count);
log("Tag: " + (time/count) + "ms per lookup");
}
catch (e) {
log("Error: " + (e.message ? e.message : String(e)));
}
}
function testid(count) {
var start;
start = new Date().getTime();
while (count-- > 0) {
if (!document.getElementById('fred')) {
throw "ID 'fred' not found";
}
}
return new Date().getTime() - start;
}
function testtag(count) {
var start;
start = new Date().getTime();
while (count-- > 0) {
if (document.getElementsByTagName('em').length == 0) {
throw "Tag 'em' not found";
}
}
return new Date().getTime() - start;
}
function log(msg) {
var log = document.getElementById('log');
log.innerHTML += "<p>" + msg + "<\/p>";
}
</script>
</head>
<body><div>
<input type='button' id='btnGo' value='Go'>
<div id='log'></div>
<hr>
<div>test test<span>test<span>test<span>test<span>test</span></span></span></span></div>
<div>test test<span>test<span>test<span>test<span>test</span></span></span></span></div>
<div>test test<span>test<span>test<span>test<span>test</span></span></span></span></div>
<div>test test<span>test<span>test<span>test<span>test</span></span></span></span></div>
<!-- repeat the above a couple of thousand times; I had about 2,200 -->
<div>test test<span>test<span>test<span>test<span>test</span></span></span></span></div>
<div>test test<span>test<span>test<span>test<em id='fred'>test</em></span></span></span></div>
</div></body>
</html>
यहां रुचि रखने वाले किसी भी व्यक्ति के लिए लाइव उदाहरण है http://jsbin.com/esemi3/ – R0MANARMY
@ROMANARMY: इसे * बहुत * अधिक सामग्री की आवश्यकता है (HTML में इनलाइन टिप्पणी देखें)। –
@ टीजे।- अच्छा परीक्षण, मैंने जेएसबीएन पर सामग्री जोड़ने की कोशिश की, लेकिन ऐसा लगता है कि उनके पास आकार सीमा है, मैंने इसे अपलोड किया है [यहां] (http://dl.dropbox.com/u/35146/js/tests/getElementById .html)। – CMS
परीक्षण करना मुश्किल नहीं होना चाहिए।
यदि यह पेड़-आधारित है तो बहुत गहरे पेड़ (जावास्क्रिप्ट के माध्यम से) बनाना एक अच्छा परीक्षण केस होना चाहिए।
कृपया प्रश्न का उत्तर दें और प्रतिनिधि पाने के लिए पोस्ट न करें। –
हां, कृपया कम से कम 3 प्रमुख ब्राउज़रों पर, वह परीक्षण करें। – Kobi
@ श्रीनिवास: क्या आपने मेरा प्रतिनिधि देखा है? मुझे परवाह नहीं है। –
विशिष्ट कार्यान्वयन HTML spec में परिभाषित नहीं किया गया है, इसलिए यह ब्राउज़र को ब्राउज़र में आसानी से बदल सकता है। उदाहरण के लिए IE documentation राज्य
आईडी या NAME विशेषता के निर्दिष्ट मान के साथ पहली वस्तु का संदर्भ देता है।
इसलिए मुझे यह कहने का लुत्फ उठाना होगा कि यह एक खोज करता है (या यह हैश टकराव के मामलों में तत्वों को फेंकता है)।
EDIT यह भी ध्यान रखें कि अन्य डेटा संरचनाएं (पेड़ों की तरह) हैं जो निरंतर और रैखिक के बीच कहीं भी पहुंचने की अनुमति देती हैं।
याद रखें कि आईई के कार्यान्वयन - आपके द्वारा उद्धृत बिट - डब्ल्यू 3 सी द्वारा निर्दिष्ट व्यवहार के साथ पूरी तरह से बाधाओं में टूटा हुआ है। उन्होंने भाग्य से IE8 में इसे ठीक किया। –
अच्छा बिंदु। निष्पक्ष डब्ल्यू 3 सी कहने के लिए ** ... व्यवहार को परिभाषित नहीं किया गया है यदि एक से अधिक तत्वों में यह आईडी है। ** यदि सही व्यवहार परिभाषित नहीं किया गया है तो तकनीकी रूप से IE गलत नहीं हो सकता है। – R0MANARMY
@ROMANARMY: गलत बिट 'id' के साथ' name' intermixing है। यदि आपके दस्तावेज़ों में डुप्लिकेट आईडी हैं, जैसा कि आप कहते हैं, जो भी ब्राउज़र करना चाहता है (उन सभी को अनदेखा करने सहित) बिल्कुल ठीक है। –
मैं फ़ायरफ़ॉक्स और वेबकिट DOM क्रियान्वयन के बारे में पता है, उन दोनों को एक hashtable का उपयोग तत्वों देखने के लिए, उनमें से स्रोत में खुदाई आप आंतरिक कार्यान्वयन करने के लिए एक तरह दे सकते हैं : यदि id
अद्वितीय है
वेबकिट कार्यान्वयन, Document.cpp, hashtable का उपयोग करता है, अन्यथा यह दस्तावेज़ को पार करता पहला मैच पाने के लिए:
Element* Document::getElementById(const AtomicString& elementId) const
{
if (elementId.isEmpty())
return 0;
m_elementsById.checkConsistency();
Element* element = m_elementsById.get(elementId.impl());//<-- hastable lookup
if (element)
return element;
if (m_duplicateIds.contains(elementId.impl())) {
// We know there's at least one node with this id,
// but we don't know what the first one is.
for (Node *n = traverseNextNode(); n != 0; n = n->traverseNextNode()) {
if (n->isElementNode()) {
element = static_cast<Element*>(n);
if (element->hasID() &&
element->getAttribute(element->idAttributeName()) == elementId) {
m_duplicateIds.remove(elementId.impl());
m_elementsById.set(elementId.impl(), element);
return element;
}
}
}
ASSERT_NOT_REACHED();
}
return 0;
}
फ़ायरफ़ॉक्स कार्यान्वयन, nsDocument.cpp
- 1. हैश टेबल लुकअप समय
- 2. एसटीएल मानचित्र में पोस्टऑर्डर ट्रैवर्सल
- 3. बाइनरी पेड़ ट्रैवर्सल की जटिलताओं
- 4. जावास्क्रिप्ट ग्राफ़ ट्रैवर्सल लाइब्रेरी
- 5. बाइनरी पेड़ स्तर ऑर्डर ट्रैवर्सल
- 6. रिवर्स हैश लुकअप क्वेरी
- 7. जावास्क्रिप्ट ट्री ट्रैवर्सल एल्गोरिदम
- 8. मानचित्र में रिवर्स लुकअप
- 9. एसक्यूएल में प्रीऑर्डर पेड़ ट्रैवर्सल के आस-पास की सूची के लिए रिकर्सिव क्वेरी?
- 10. हैश मैप लुकअप के लिए अनुकूलित
- 11. getElementById ASP.net
- 12. एनमैप या हैश मैप यदि लुकअप कुंजी स्ट्रिंग
- 13. हास्केल मानचित्र पेड़
- 14. कोई जावा हैश पेड़ कार्यान्वयन?
- 15. इनऑर्डर ट्रैवर्सल
- 16. बीजगणितीय डेटा प्रकारों के रिकर्सिव तल-अप ट्रैवर्सल
- 17. हैश टेबल वी/एस पेड़
- 18. हैश टेबल बनाम हैश सूची बनाम हैश पेड़ बनाम?
- 19. जावास्क्रिप्ट getElementByID() काम नहीं कर रहा है
- 20. हैश टेबल लुकअप - सही हैश के साथ, सी
- 21. धागा सुरक्षित हैश मानचित्र?
- 22. पायथन में हैश मानचित्र
- 23. 'मौजूद' का उपयोग कर अतिरिक्त हैश लुकअप?
- 24. प्री-ऑर्डर ट्रैवर्सल के साथ पेड़ का निर्माण
- 25. getElementById और शून्य - क्यों?
- 26. रिकर्सिव और पुनरावर्तक डीएनएस लुकअप के बीच अंतर
- 27. पेड़ के ट्रैवर्सल की समय जटिलता क्या है?
- 28. असली दुनिया प्री/पोस्ट-ऑर्डर पेड़ ट्रैवर्सल उदाहरण
- 29. जावास्क्रिप्ट हैश
- 30. लुकअप मानचित्र/हैश के लिए एक अच्छा नामकरण सम्मेलन क्या है?
+1, अच्छा सवाल। एक बहुत अच्छे सवाल के लिए –
+1। – Kangkan
मुझे पूरा यकीन नहीं है कि यह एक अच्छा सवाल है। एक अच्छा सवाल हो सकता है "किसी दिए गए आईडी के साथ तत्व ढूंढने का सबसे अच्छा तरीका क्या है", और 'getElementById' संभवतः सबसे अच्छा जवाब है। इसे कैसे कार्यान्वित किया जाता है? वह एक काले बॉक्स में peeping है। एक निश्चित उत्तर के लिए शायद बहुत सारे ब्राउज़र हैं। – Kobi