difftreelog
perf implement std.findSubstr in native
in: master
4 files changed
Cargo.tomldiffbeforeafterboth8opt-level = 38opt-level = 39lto = "fat"9lto = "fat"10codegen-units = 110codegen-units = 111# debug = 011debug = 012panic = "abort"12panic = "abort"13# strip = true13strip = true1414crates/jrsonnet-evaluator/src/val.rsdiffbeforeafterboth--- a/crates/jrsonnet-evaluator/src/val.rs
+++ b/crates/jrsonnet-evaluator/src/val.rs
@@ -206,9 +206,13 @@
pub fn new_eager() -> Self {
Self::Eager(Cc::new(Vec::new()))
}
+ pub fn empty() -> Self {
+ Self::new_range(0, 0)
+ }
/// # Panics
/// If a > b
+ #[inline]
pub fn new_range(a: i32, b: i32) -> Self {
assert!(a <= b);
Self::Range(a, b)
crates/jrsonnet-stdlib/src/lib.rsdiffbeforeafterboth--- a/crates/jrsonnet-stdlib/src/lib.rs
+++ b/crates/jrsonnet-stdlib/src/lib.rs
@@ -128,6 +128,7 @@
("splitLimit".into(), builtin_splitlimit::INST),
("asciiUpper".into(), builtin_ascii_upper::INST),
("asciiLower".into(), builtin_ascii_lower::INST),
+ ("findSubstr".into(), builtin_find_substr::INST),
]
.iter()
.cloned()
@@ -420,3 +421,28 @@
fn builtin_ascii_lower(str: IStr) -> Result<String> {
Ok(str.to_ascii_lowercase())
}
+
+#[builtin]
+fn builtin_find_substr(pat: IStr, str: IStr) -> Result<ArrValue> {
+ if pat.is_empty() || str.is_empty() || pat.len() > str.len() {
+ return Ok(ArrValue::empty());
+ }
+
+ let str = str.as_str();
+ let pat = pat.as_bytes();
+ let strb = str.as_bytes();
+
+ let max_pos = str.len() - pat.len();
+
+ let mut out: Vec<Val> = Vec::new();
+ for (ch_idx, (i, _)) in str
+ .char_indices()
+ .take_while(|(i, _)| i <= &max_pos)
+ .enumerate()
+ {
+ if &strb[i..i + pat.len()] == pat {
+ out.push(Val::Num(ch_idx as f64))
+ }
+ }
+ Ok(out.into())
+}
crates/jrsonnet-stdlib/src/std.jsonnetdiffbeforeafterboth--- a/crates/jrsonnet-stdlib/src/std.jsonnet
+++ b/crates/jrsonnet-stdlib/src/std.jsonnet
@@ -477,19 +477,6 @@
} else
a,
- findSubstr(pat, str)::
- if !std.isString(pat) then
- error 'findSubstr first parameter should be a string, got ' + std.type(pat)
- else if !std.isString(str) then
- error 'findSubstr second parameter should be a string, got ' + std.type(str)
- else
- local pat_len = std.length(pat);
- local str_len = std.length(str);
- if pat_len == 0 || str_len == 0 || pat_len > str_len then
- []
- else
- std.filter(function(i) str[i:i + pat_len] == pat, std.range(0, str_len - pat_len)),
-
find(value, arr)::
if !std.isArray(arr) then
error 'find second parameter should be an array, got ' + std.type(arr)