feature. See also
. The project being documented here (as the example) is the Zig library itself.
main.query_exec_fallible
fn query_exec_fallible(query: []const u8, ignore_case: bool) !void
File
Code
fn query_exec_fallible(query: []const u8, ignore_case: bool) !void {
const Score = packed struct(u32) {
points: u16,
segments: u16,
};
const g = struct {
var full_path_search_text: ArrayList(u8) = .empty;
var full_path_search_text_lower: ArrayList(u8) = .empty;
var doc_search_text: ArrayList(u8) = .empty;
var scores: ArrayList(Score) = .empty;
};
try query_results.resize(gpa, 1);
try g.scores.resize(gpa, 1);
decl_loop: for (Walk.decls.items, 0..) |*decl, decl_index| {
const info = decl.extra_info();
if (!info.is_pub) continue;
try decl.reset_with_path(&g.full_path_search_text);
if (decl.parent != .none)
try Decl.append_parent_ns(&g.full_path_search_text, decl.parent);
try g.full_path_search_text.appendSlice(gpa, info.name);
try g.full_path_search_text_lower.resize(gpa, g.full_path_search_text.items.len);
@memcpy(g.full_path_search_text_lower.items, g.full_path_search_text.items);
const ast = decl.file.get_ast();
if (info.first_doc_comment.unwrap()) |first_doc_comment| {
try collect_docs(&g.doc_search_text, ast, first_doc_comment);
}
if (ignore_case) {
ascii_lower(g.full_path_search_text_lower.items);
ascii_lower(g.doc_search_text.items);
}
var it = std.mem.tokenizeScalar(u8, query, ' ');
var points: u16 = 0;
var bypass_limit = false;
while (it.next()) |term| {
if (std.mem.eql(u8, g.full_path_search_text.items, term)) {
points += 4;
bypass_limit = true;
continue;
}
if (std.mem.eql(u8, info.name, term)) {
points += 3;
bypass_limit = true;
continue;
}
if (std.mem.indexOf(u8, g.full_path_search_text_lower.items, term) != null) {
points += 2;
continue;
}
if (std.mem.indexOf(u8, g.doc_search_text.items, term) != null) {
points += 1;
continue;
}
continue :decl_loop;
}
if (query_results.items.len < max_matched_items or bypass_limit) {
try query_results.append(gpa, @fromBackingInt(@intCast(decl_index)));
try g.scores.append(gpa, .{
.points = points,
.segments = @intCast(count_scalar(g.full_path_search_text.items, '.')),
});
}
}
const sort_context: struct {
pub fn swap(sc: @This(), a_index: usize, b_index: usize) void {
_ = sc;
std.mem.swap(Score, &g.scores.items[a_index], &g.scores.items[b_index]);
std.mem.swap(Decl.Index, &query_results.items[a_index], &query_results.items[b_index]);
}
pub fn lessThan(sc: @This(), a_index: usize, b_index: usize) bool {
_ = sc;
const a_score = g.scores.items[a_index];
const b_score = g.scores.items[b_index];
if (b_score.points < a_score.points) {
return true;
} else if (b_score.points > a_score.points) {
return false;
} else if (a_score.segments < b_score.segments) {
return true;
} else if (a_score.segments > b_score.segments) {
return false;
} else {
const a_decl = query_results.items[a_index];
const b_decl = query_results.items[b_index];
const a_file_path = a_decl.get().file.path();
const b_file_path = b_decl.get().file.path();
return std.mem.lessThan(u8, b_file_path, a_file_path);
}
}
} = .{};
std.mem.sortUnstableContext(1, query_results.items.len, sort_context);
if (query_results.items.len > max_matched_items)
query_results.shrinkRetainingCapacity(max_matched_items);
}