mirror of
https://github.com/roc-lang/roc.git
synced 2025-10-02 16:21:11 +00:00
actually infer the size
This commit is contained in:
parent
c00cd2f415
commit
e9f5c1a73c
8 changed files with 51 additions and 25 deletions
|
@ -1012,7 +1012,7 @@ fn canonicalize_pending_def<'a>(
|
|||
function_type,
|
||||
closure_type,
|
||||
return_type,
|
||||
name: *symbol,
|
||||
name: *defined_symbol,
|
||||
recursive: is_recursive,
|
||||
arguments: arguments.clone(),
|
||||
loc_body: body.clone(),
|
||||
|
@ -1145,7 +1145,7 @@ fn canonicalize_pending_def<'a>(
|
|||
function_type,
|
||||
closure_type,
|
||||
return_type,
|
||||
name: *symbol,
|
||||
name: *defined_symbol,
|
||||
recursive: is_recursive,
|
||||
arguments: arguments.clone(),
|
||||
loc_body: body.clone(),
|
||||
|
|
|
@ -961,6 +961,7 @@ pub fn constrain_decls(
|
|||
Vec::new(),
|
||||
constrain_def(&env, def, constraint),
|
||||
);
|
||||
debug_assert!(format!("{:?}", &constraint).contains("SaveTheEnvironment"));
|
||||
}
|
||||
Declaration::DeclareRec(defs) => {
|
||||
constraint = exists_with_aliases(
|
||||
|
@ -968,6 +969,7 @@ pub fn constrain_decls(
|
|||
Vec::new(),
|
||||
constrain_recursive_defs(&env, defs, constraint),
|
||||
);
|
||||
debug_assert!(format!("{:?}", &constraint).contains("SaveTheEnvironment"));
|
||||
}
|
||||
Declaration::InvalidCycle(_, _) => {
|
||||
// invalid cycles give a canonicalization error. we skip them here.
|
||||
|
@ -976,6 +978,7 @@ pub fn constrain_decls(
|
|||
}
|
||||
}
|
||||
|
||||
debug_assert!(format!("{:?}", &constraint).contains("SaveTheEnvironment"));
|
||||
constraint
|
||||
}
|
||||
|
||||
|
|
|
@ -45,7 +45,7 @@ pub fn helper_without_uniqueness<'a>(
|
|||
|
||||
let subs = Subs::new(var_store.into());
|
||||
let mut unify_problems = Vec::new();
|
||||
let (content, mut subs) = infer_expr(subs, &mut unify_problems, &constraint, var);
|
||||
let (content, mut subs, solve_env) = infer_expr(subs, &mut unify_problems, &constraint, var);
|
||||
|
||||
assert_eq!(
|
||||
unify_problems,
|
||||
|
@ -103,7 +103,7 @@ pub fn helper_without_uniqueness<'a>(
|
|||
};
|
||||
|
||||
// infer the size of any closures
|
||||
roc_mono::closures::infer_closure_size(&loc_expr.value, mono_env.subs);
|
||||
roc_mono::closures::infer_closure_size(&loc_expr.value, mono_env.subs, &solve_env);
|
||||
|
||||
let main_body = roc_mono::ir::Stmt::new(&mut mono_env, loc_expr.value, &mut procs);
|
||||
|
||||
|
@ -219,7 +219,7 @@ pub fn helper_with_uniqueness<'a>(
|
|||
assert_eq!(errors, Vec::new(), "Encountered errors: {:?}", errors);
|
||||
|
||||
let mut unify_problems = Vec::new();
|
||||
let (content, mut subs) = infer_expr(subs, &mut unify_problems, &constraint, var);
|
||||
let (content, mut subs, solve_env) = infer_expr(subs, &mut unify_problems, &constraint, var);
|
||||
|
||||
assert_eq!(
|
||||
unify_problems,
|
||||
|
@ -275,7 +275,7 @@ pub fn helper_with_uniqueness<'a>(
|
|||
};
|
||||
|
||||
// infer the size of any closures
|
||||
roc_mono::closures::infer_closure_size(&loc_expr.value, mono_env.subs);
|
||||
roc_mono::closures::infer_closure_size(&loc_expr.value, mono_env.subs, &solve_env);
|
||||
|
||||
let main_body = roc_mono::ir::Stmt::new(&mut mono_env, loc_expr.value, &mut procs);
|
||||
let mut headers = {
|
||||
|
|
|
@ -74,16 +74,16 @@ pub fn infer_expr(
|
|||
problems: &mut Vec<roc_solve::solve::TypeError>,
|
||||
constraint: &Constraint,
|
||||
expr_var: Variable,
|
||||
) -> (Content, Subs) {
|
||||
) -> (Content, Subs, solve::Env) {
|
||||
let env = solve::Env {
|
||||
aliases: MutMap::default(),
|
||||
vars_by_symbol: SendMap::default(),
|
||||
};
|
||||
let (solved, _) = solve::run(&env, problems, subs, constraint);
|
||||
let (solved, env) = solve::run(&env, problems, subs, constraint);
|
||||
|
||||
let content = solved.inner().get_without_compacting(expr_var).content;
|
||||
|
||||
(content, solved.into_inner())
|
||||
(content, solved.into_inner(), env)
|
||||
}
|
||||
|
||||
pub fn parse_loc_with<'a>(arena: &'a Bump, input: &'a str) -> Result<Located<ast::Expr<'a>>, Fail> {
|
||||
|
|
|
@ -6,19 +6,22 @@ use roc_collections::all::MutSet;
|
|||
use roc_constrain::expr::exists;
|
||||
use roc_module::symbol::Symbol;
|
||||
use roc_region::all::Region;
|
||||
use roc_solve::solve;
|
||||
use roc_types::subs::{Subs, VarStore};
|
||||
use roc_types::types::{Category, Type};
|
||||
|
||||
pub fn infer_closure_size(expr: &Expr, subs: &mut Subs) {
|
||||
use roc_solve::solve;
|
||||
|
||||
pub fn infer_closure_size(expr: &Expr, subs: &mut Subs, solve_env: &solve::Env) {
|
||||
let mut var_store = VarStore::new_from_subs(subs);
|
||||
|
||||
let env = solve::Env::default();
|
||||
let mut problems = Vec::new();
|
||||
let constraint = generate_constraint(expr, &mut var_store);
|
||||
|
||||
let _new_env = solve::run_in_place(&env, &mut problems, subs, &constraint);
|
||||
let next = var_store.fresh().index();
|
||||
let variables_introduced = next as usize - (subs.len() - 1);
|
||||
|
||||
subs.extend_by(variables_introduced);
|
||||
|
||||
let _new_env = solve::run_in_place(solve_env, &mut problems, subs, &constraint);
|
||||
|
||||
debug_assert_eq!(problems.len(), 0);
|
||||
}
|
||||
|
@ -224,7 +227,8 @@ pub fn generate_constraints_help(
|
|||
}
|
||||
|
||||
Closure {
|
||||
arguments: _,
|
||||
arguments,
|
||||
name,
|
||||
closure_type: closure_var,
|
||||
loc_body: boxed_body,
|
||||
..
|
||||
|
@ -232,7 +236,18 @@ pub fn generate_constraints_help(
|
|||
let mut cons = Vec::new();
|
||||
let mut variables = Vec::new();
|
||||
|
||||
let closed_over_symbols = MutSet::default();
|
||||
let bound_by_closure = arguments
|
||||
.iter()
|
||||
.map(|(_, pattern)| symbols_from_pattern(&pattern.value))
|
||||
.flatten()
|
||||
.collect::<MutSet<_>>();
|
||||
|
||||
// let closed_over_symbols = MutSet::default();
|
||||
let closed_over_symbols = free_variables(expr)
|
||||
.into_iter()
|
||||
.filter(|x| !x.is_builtin() && !bound_by_closure.contains(&x) && !(x == name))
|
||||
.collect::<MutSet<_>>();
|
||||
|
||||
let closure_ext_var = var_store.fresh();
|
||||
let closure_var = *closure_var;
|
||||
|
||||
|
|
|
@ -196,8 +196,9 @@ fn solve(
|
|||
constraint: &Constraint,
|
||||
) -> State {
|
||||
match constraint {
|
||||
True => state,
|
||||
SaveTheEnvironment => {
|
||||
// True => state,
|
||||
True | SaveTheEnvironment => {
|
||||
// NOTE deviation: elm only copies the env into the state on SaveTheEnvironment
|
||||
let mut copy = state;
|
||||
|
||||
copy.env = env.clone();
|
||||
|
|
|
@ -73,6 +73,7 @@ impl VarStore {
|
|||
}
|
||||
|
||||
pub fn new_from_subs(subs: &Subs) -> Self {
|
||||
// TODO why -2, are we not overwriting something here?
|
||||
let next_var = (subs.utable.len() - 1) as u32;
|
||||
debug_assert!(next_var >= Variable::FIRST_USER_SPACE_VAR.0);
|
||||
|
||||
|
@ -266,6 +267,12 @@ impl Subs {
|
|||
subs
|
||||
}
|
||||
|
||||
pub fn extend_by(&mut self, entries: usize) {
|
||||
for _ in 0..entries {
|
||||
self.utable.new_key(flex_var_descriptor());
|
||||
}
|
||||
}
|
||||
|
||||
pub fn fresh(&mut self, value: Descriptor) -> Variable {
|
||||
self.utable.new_key(value)
|
||||
}
|
||||
|
|
|
@ -133,13 +133,13 @@ fn unify_context(subs: &mut Subs, pool: &mut Pool, ctx: Context) -> Outcome {
|
|||
// NOTE: names are generated here (when creating an error type) and that modifies names
|
||||
// generated by pretty_print.rs. So many test will fail with changes in variable names when
|
||||
// this block runs.
|
||||
let (type1, _problems1) = subs.var_to_error_type(ctx.first);
|
||||
let (type2, _problems2) = subs.var_to_error_type(ctx.second);
|
||||
println!("\n --------------- \n");
|
||||
dbg!(ctx.first, type1);
|
||||
println!("\n --- \n");
|
||||
dbg!(ctx.second, type2);
|
||||
println!("\n --------------- \n");
|
||||
// let (type1, _problems1) = subs.var_to_error_type(ctx.first);
|
||||
// let (type2, _problems2) = subs.var_to_error_type(ctx.second);
|
||||
// println!("\n --------------- \n");
|
||||
// dbg!(ctx.first, type1);
|
||||
// println!("\n --- \n");
|
||||
// dbg!(ctx.second, type2);
|
||||
// println!("\n --------------- \n");
|
||||
println!(
|
||||
"{:?} {:?} ~ {:?} {:?}",
|
||||
ctx.first,
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue