aboutsummaryrefslogtreecommitdiff
path: root/crates/libanalysis/src
diff options
context:
space:
mode:
authorAleksey Kladov <[email protected]>2018-08-13 15:19:27 +0100
committerAleksey Kladov <[email protected]>2018-08-13 15:19:27 +0100
commit5a56ac4b72e7f57fb20d49bcf531611f144cc0e0 (patch)
tree895b810cdebc1afa199133b17441339fdf4e1ff0 /crates/libanalysis/src
parent8ae56fa6d0e8a03d6ad75919d6be953f5fc27083 (diff)
Better limiting
Diffstat (limited to 'crates/libanalysis/src')
-rw-r--r--crates/libanalysis/src/lib.rs20
-rw-r--r--crates/libanalysis/src/symbol_index.rs18
2 files changed, 27 insertions, 11 deletions
diff --git a/crates/libanalysis/src/lib.rs b/crates/libanalysis/src/lib.rs
index 97b6dfca6..562fab290 100644
--- a/crates/libanalysis/src/lib.rs
+++ b/crates/libanalysis/src/lib.rs
@@ -94,12 +94,12 @@ impl World {
94 Ok(index.clone()) 94 Ok(index.clone())
95 } 95 }
96 96
97 pub fn world_symbols<'a>(&'a self, query: Query) -> impl Iterator<Item=(&'a Path, &'a FileSymbol)> + 'a { 97 pub fn world_symbols<'a>(&'a self, mut query: Query) -> impl Iterator<Item=(&'a Path, &'a FileSymbol)> + 'a {
98 self.data.file_map.iter() 98 self.data.file_map.iter()
99 .flat_map(move |(path, data)| { 99 .flat_map(move |(path, data)| {
100 let path: &'a Path = path.as_path(); 100 let path: &'a Path = path.as_path();
101 let symbols = data.symbols(path); 101 let symbols = data.symbols();
102 query.process(symbols).map(move |s| (path, s)) 102 query.process(symbols).into_iter().map(move |s| (path, s))
103 }) 103 })
104 } 104 }
105 105
@@ -125,7 +125,8 @@ impl World {
125 125
126 let mut query = Query::new(name.to_string()); 126 let mut query = Query::new(name.to_string());
127 query.exact(); 127 query.exact();
128 Ok(self.world_symbols(query).take(4).collect()) 128 query.limit(4);
129 Ok(self.world_symbols(query).collect())
129 } 130 }
130 131
131 fn file_data(&self, path: &Path) -> Result<Arc<FileData>> { 132 fn file_data(&self, path: &Path) -> Result<Arc<FileData>> {
@@ -178,9 +179,14 @@ impl FileData {
178 }) 179 })
179 } 180 }
180 181
181 fn symbols(&self, path: &Path) -> &FileSymbols { 182 fn syntax_transient(&self) -> ast::File {
182 let syntax = self.syntax(path); 183 self.syntax.get().map(|s| s.clone())
184 .unwrap_or_else(|| ast::File::parse(&self.text))
185 }
186
187 fn symbols(&self) -> &FileSymbols {
188 let syntax = self.syntax_transient();
183 self.symbols 189 self.symbols
184 .get_or_init(|| FileSymbols::new(syntax)) 190 .get_or_init(|| FileSymbols::new(&syntax))
185 } 191 }
186} 192}
diff --git a/crates/libanalysis/src/symbol_index.rs b/crates/libanalysis/src/symbol_index.rs
index 88d5c4995..a7ae197e0 100644
--- a/crates/libanalysis/src/symbol_index.rs
+++ b/crates/libanalysis/src/symbol_index.rs
@@ -35,6 +35,7 @@ pub struct Query {
35 lowercased: String, 35 lowercased: String,
36 only_types: bool, 36 only_types: bool,
37 exact: bool, 37 exact: bool,
38 limit: usize,
38} 39}
39 40
40impl Query { 41impl Query {
@@ -45,6 +46,7 @@ impl Query {
45 lowercased, 46 lowercased,
46 only_types: false, 47 only_types: false,
47 exact: false, 48 exact: false,
49 limit: usize::max_value()
48 } 50 }
49 } 51 }
50 52
@@ -56,10 +58,14 @@ impl Query {
56 self.exact = true; 58 self.exact = true;
57 } 59 }
58 60
61 pub fn limit(&mut self, limit: usize) {
62 self.limit = limit
63 }
64
59 pub(crate) fn process<'a>( 65 pub(crate) fn process<'a>(
60 &self, 66 &mut self,
61 file: &'a FileSymbols, 67 file: &'a FileSymbols,
62 ) -> impl Iterator<Item=&'a FileSymbol> + 'a { 68 ) -> Vec<&'a FileSymbol> {
63 fn is_type(kind: SyntaxKind) -> bool { 69 fn is_type(kind: SyntaxKind) -> bool {
64 match kind { 70 match kind {
65 STRUCT | ENUM | TRAIT | TYPE_ITEM => true, 71 STRUCT | ENUM | TRAIT | TYPE_ITEM => true,
@@ -70,6 +76,9 @@ impl Query {
70 let mut stream = file.map.search(automaton).into_stream(); 76 let mut stream = file.map.search(automaton).into_stream();
71 let mut res = Vec::new(); 77 let mut res = Vec::new();
72 while let Some((_, idx)) = stream.next() { 78 while let Some((_, idx)) = stream.next() {
79 if self.limit == 0 {
80 break;
81 }
73 let idx = idx as usize; 82 let idx = idx as usize;
74 let symbol = &file.symbols[idx]; 83 let symbol = &file.symbols[idx];
75 if self.only_types && !is_type(symbol.kind) { 84 if self.only_types && !is_type(symbol.kind) {
@@ -78,9 +87,10 @@ impl Query {
78 if self.exact && symbol.name != self.query { 87 if self.exact && symbol.name != self.query {
79 continue; 88 continue;
80 } 89 }
81 res.push(symbol) 90 res.push(symbol);
91 self.limit -= 1;
82 } 92 }
83 res.into_iter() 93 res
84 } 94 }
85} 95}
86 96