Index: third_party/WebKit/Source/build/scripts/make_element_lookup_trie.py |
diff --git a/third_party/WebKit/Source/build/scripts/make_element_lookup_trie.py b/third_party/WebKit/Source/build/scripts/make_element_lookup_trie.py |
index 90b696d0c22b83aa0eb1de8fc69b3b559431e477..79221a17f6c3cc529f0b0602f57588a38c48a137 100755 |
--- a/third_party/WebKit/Source/build/scripts/make_element_lookup_trie.py |
+++ b/third_party/WebKit/Source/build/scripts/make_element_lookup_trie.py |
@@ -27,6 +27,7 @@ |
# (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE |
# OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. |
+from collections import OrderedDict |
from itertools import groupby, islice |
import sys |
@@ -36,7 +37,7 @@ import template_expander |
PARAMETER_NAME = 'data' |
-def _trie(tags, index): |
+def _trie(str_to_return_value_dict, index): |
"""Make a trie from list of tags, starting at index. |
Resulting trie is partly space-optimized (semi-radix tree): once have only |
@@ -44,39 +45,47 @@ def _trie(tags, index): |
However, does not compact branch nodes with a single child. (FIXME) |
Returns: |
- (char, subtrie, tag, conditions): (char, trie, str, list) |
- code generation differs between branch nodes and leaf nodes, |
- hence need different data for each. |
+ dict(char, subtrie, string, value, conditions): |
Timothy Loh
2016/05/03 07:40:25
Can we return something structured like (e.g.)
{
meade_UTC10
2016/05/04 07:24:54
Done.
|
+ char, list, string, string, string. Code generation differs between |
+ branch nodes and leaf nodes, hence need different data for each. |
Arguments: |
- tags: sorted list |
- (sorted needed by groupby, list needed by len) |
+ str_to_return_value_dict: A ordered dictionary of strings to the return |
+ value strings. Ordered by length, then alphabetically. |
index: index at which to branch |
- (assumes prior to this index strings have a common prefix) |
""" |
def trie_node(char, subtags_iter): |
# Pass in |char| so we can include in same tuple without unpacking |
subtags = list(subtags_iter) # need list for len |
if len(subtags) == 1: # terminal node, no subtrie |
- subtrie = None |
tag = subtags[0] |
- conditions = _conditions(tag, index + 1) |
+ return { |
+ 'char': char, |
+ 'subtrie': None, |
+ 'string': tag, |
+ 'value': subtags_iter[tag], |
+ 'conditions': _conditions(tag, index + 1) |
+ } |
else: |
- subtrie = _trie(subtags, index + 1) |
- tag = None |
- conditions = None |
- return char, subtrie, tag, conditions |
+ return { |
+ 'char': char, |
+ 'subtrie': _trie(subtags_iter, index + 1), |
+ 'string': None, |
+ 'value': None, |
+ 'conditions': None |
+ } |
# Group by char at index |
- def char_at_index(tag): |
- return tag[index].lower() |
+ def char_at_index(string): |
+ return string[index].lower() |
- char_subtags = ((k, g) for k, g in groupby(tags, char_at_index)) |
+ char_subtags = [] |
+ for k, g in groupby(str_to_return_value_dict, char_at_index): |
Timothy Loh
2016/05/03 07:40:25
same comment as other place about groupby/OrderedD
meade_UTC10
2016/05/04 07:24:54
Done.
|
+ sub_dict = OrderedDict( |
+ [(inner_key, str_to_return_value_dict[inner_key]) for inner_key in g]) |
+ char_subtags.append((k, sub_dict)) |
- # FIXME: if all subtags have a common prefix, merge with child |
- # and skip the switch in the generated code |
- |
- return (trie_node(char, subtags) for char, subtags in char_subtags) |
+ return [trie_node(char, subtags) for char, subtags in char_subtags] |
def _conditions(tag, index): |
Timothy Loh
2016/05/03 07:40:25
as discussed, let's move all of the logic for this
meade_UTC10
2016/05/04 07:24:54
Done.
|
@@ -86,6 +95,19 @@ def _conditions(tag, index): |
for i, c in islice(enumerate(tag), index, None)] |
+def _trie_list(str_to_return_value_dict): |
+ ordered_dict = OrderedDict( |
Timothy Loh
2016/05/03 07:40:25
OrderedDict+groupby seems weird here, probably bet
meade_UTC10
2016/05/04 07:24:54
Done.
|
+ sorted(str_to_return_value_dict.items(), key=lambda pair: (len(pair[0]), pair[0]))) |
+ |
+ dicts = [] |
+ for k, g in groupby(ordered_dict, len): |
+ sub_dict = OrderedDict( |
+ [(inner_key, str_to_return_value_dict[inner_key]) for inner_key in g]) |
+ dicts.append((k, sub_dict)) |
+ |
+ return [(length, _trie(d, 0)) for length, d in dicts] |
+ |
+ |
class ElementLookupTrieWriter(in_generator.Writer): |
# FIXME: Inherit all these from somewhere. |
defaults = { |
@@ -108,7 +130,9 @@ class ElementLookupTrieWriter(in_generator.Writer): |
def __init__(self, in_file_paths): |
super(ElementLookupTrieWriter, self).__init__(in_file_paths) |
- self._tags = [entry['name'] for entry in self.in_file.name_dictionaries] |
+ self._tags = {} |
+ for entry in self.in_file.name_dictionaries: |
+ self._tags[entry['name']] = entry['name'] |
self._namespace = self.in_file.parameters['namespace'].strip('"') |
self._outputs = { |
(self._namespace + 'ElementLookupTrie.h'): self.generate_header, |
@@ -123,15 +147,9 @@ class ElementLookupTrieWriter(in_generator.Writer): |
@template_expander.use_jinja('ElementLookupTrie.cpp.tmpl') |
def generate_implementation(self): |
- # First sort, so groupby works |
- self._tags.sort(key=lambda tag: (len(tag), tag)) |
- # Group tags by length |
- length_tags = ((k, g) for k, g in groupby(self._tags, len)) |
- |
return { |
'namespace': self._namespace, |
- 'length_tries': ((length, _trie(tags, 0)) |
- for length, tags in length_tags), |
+ 'length_tries': _trie_list(self._tags) |
} |