Implement List.any

This commit is contained in:
Kevin Sjöberg 2021-11-05 23:34:10 +01:00
parent 0e500ba33c
commit 44938a9e35
15 changed files with 137 additions and 6 deletions

View file

@ -967,7 +967,6 @@ fn call_spec(
add_loop(builder, block, state_type, init_state, loop_body)
}
ListKeepIf { xs } => {
let list = env.symbols[xs];
@ -1073,6 +1072,25 @@ fn call_spec(
let state_layout = Layout::Builtin(Builtin::List(&output_element_layout));
let state_type = layout_spec(builder, &state_layout)?;
add_loop(builder, block, state_type, init_state, loop_body)
}
ListAny { xs } => {
let list = env.symbols[xs];
let loop_body = |builder: &mut FuncDefBuilder, block, _state| {
let bag = builder.add_get_tuple_field(block, list, LIST_BAG_INDEX)?;
let element = builder.add_bag_get(block, bag)?;
let new_state = call_function!(builder, block, [element]);
Ok(new_state)
};
let state_layout = Layout::Builtin(Builtin::Int1);
let state_type = layout_spec(builder, &state_layout)?;
let init_state = new_num(builder, block)?;
add_loop(builder, block, state_type, init_state, loop_body)
}
}

View file

@ -617,7 +617,8 @@ impl<'a> BorrowInfState<'a> {
ListMap { xs }
| ListKeepIf { xs }
| ListKeepOks { xs }
| ListKeepErrs { xs } => {
| ListKeepErrs { xs }
| ListAny { xs } => {
// own the list if the function wants to own the element
if !function_ps[0].borrow {
self.own_var(*xs);
@ -949,7 +950,7 @@ pub fn lowlevel_borrow_signature(arena: &Bump, op: LowLevel) -> &[bool] {
ListMap2 => arena.alloc_slice_copy(&[owned, owned, function, closure_data]),
ListMap3 => arena.alloc_slice_copy(&[owned, owned, owned, function, closure_data]),
ListMap4 => arena.alloc_slice_copy(&[owned, owned, owned, owned, function, closure_data]),
ListKeepIf | ListKeepOks | ListKeepErrs => {
ListKeepIf | ListKeepOks | ListKeepErrs | ListAny => {
arena.alloc_slice_copy(&[owned, function, closure_data])
}
ListContains => arena.alloc_slice_copy(&[borrowed, irrelevant]),

View file

@ -530,7 +530,8 @@ impl<'a> Context<'a> {
ListMap { xs }
| ListKeepIf { xs }
| ListKeepOks { xs }
| ListKeepErrs { xs } => {
| ListKeepErrs { xs }
| ListAny { xs } => {
let borrows = [function_ps[0].borrow, FUNCTION, CLOSURE_DATA];
let b = self.add_dec_after_lowlevel(arguments, &borrows, b, b_live_vars);

View file

@ -4113,6 +4113,11 @@ pub fn with_hole<'a>(
let xs = arg_symbols[0];
match_on_closure_argument!(ListKeepIf, [xs])
}
ListAny => {
debug_assert_eq!(arg_symbols.len(), 2);
let xs = arg_symbols[0];
match_on_closure_argument!(ListAny, [xs])
}
ListKeepOks => {
debug_assert_eq!(arg_symbols.len(), 2);
let xs = arg_symbols[0];

View file

@ -47,6 +47,9 @@ pub enum HigherOrder {
ListSortWith {
xs: Symbol,
},
ListAny {
xs: Symbol,
},
DictWalk {
xs: Symbol,
state: Symbol,
@ -69,6 +72,7 @@ impl HigherOrder {
HigherOrder::ListKeepErrs { .. } => 1,
HigherOrder::ListSortWith { .. } => 2,
HigherOrder::DictWalk { .. } => 2,
HigherOrder::ListAny { .. } => 1,
}
}
}