Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

How to use generic ViewMut with_id? #191

Open
SSSxCCC opened this issue Feb 1, 2024 · 1 comment
Open

How to use generic ViewMut with_id? #191

SSSxCCC opened this issue Feb 1, 2024 · 1 comment

Comments

@SSSxCCC
Copy link

SSSxCCC commented Feb 1, 2024

#157 use some bounds to make generic ViewMut iterator work, but I still can not make generic ViewMut with_id work:

trait MutTrait {
    fn mutmut(&mut self);
}

fn expected<T: Component + MutTrait>(mut v: ViewMut<T>)
where
    for<'a, 'b> &'a mut ViewMut<'b, T>: IntoIter,
    for<'a, 'b> <<&'a mut ViewMut<'b, T> as IntoIter>::IntoIter as Iterator>::Item: std::ops::DerefMut<Target = T>,
{
    for mut x in (&mut v).iter() {
        x.mutmut();
    }
}

fn weird<T: Component + MutTrait>(mut v: ViewMut<T>)
where
    for<'a, 'b> &'a mut ViewMut<'b, T>: IntoIter,
    for<'a, 'b> <<&'a mut ViewMut<'b, T> as IntoIter>::IntoIter as Iterator>::Item: std::ops::DerefMut<Target = T>,
    for<'a, 'b> <&'a mut ViewMut<'b, T> as shipyard::IntoIter>::IntoIter: IntoWithId,
    for<'a, 'b> WithId<<&'a mut ViewMut<'b, T> as shipyard::IntoIter>::IntoIter>: Iterator,
    for<'a, 'b> <WithId<<&'a mut ViewMut<'b, T> as shipyard::IntoIter>::IntoIter> as Iterator>::Item: std::ops::DerefMut<Target = (EntityId, dyn std::ops::DerefMut<Target = T>)>
{
    for (id, x) in (&mut v).iter().with_id() { // error: expected associated type, found `(_, _)`
        x.mutmut();
    }
}

I try to add bounds but I still can not make it work.
Please help me, thanks!

@leudz
Copy link
Owner

leudz commented Feb 9, 2024

This should work but doesn't for some lifetime reason.

// `IntoAbstract` would have to be implemented for the type `&'0 mut shipyard::ViewMut<'1, Component1>`, for any two lifetimes `'0` and `'1`...
// ...but `IntoAbstract` is actually implemented for the type `&mut shipyard::ViewMut<'2, Component1>`, for some specific lifetime `'2` 
fn weird<T: Component + MutTrait>(mut v: ViewMut<T>)
where
    for<'a, 'b> &'a mut ViewMut<'b, T>: IntoIter,
    for<'a, 'b> <<&'a mut ViewMut<'b, T> as IntoIter>::IntoIter as Iterator>::Item:
        std::ops::DerefMut<Target = T>,
    for<'a, 'b> <&'a mut ViewMut<'b, T> as IntoIter>::IntoIter: Iterator + LastId,
{
    for (id, mut x) in WithId((&mut v).iter()) {
        x.mutmut();
    }
}

And turns out the code in the issue you linked has the same issue. So I'm not sure it ever worked 😰


In theory something like this should also work:

fn weird<T: Component + MutTrait>(mut v: ViewMut<T>)
where
    for<'a, 'b> &'a mut ViewMut<'b, T>: IntoIter,
    for<'a, 'b> <<&'a mut ViewMut<'b, T> as IntoIter>::IntoIter as Iterator>::Item:
        std::ops::DerefMut<Target = T>,
    // binding for associated type `Item` references lifetime `'a`, which does not appear in the trait input types
    // binding for associated type `Item` references lifetime `'b`, which does not appear in the trait input types
    for<'a, 'b> WithId<<&'a mut ViewMut<'b, T> as IntoIter>::IntoIter>: Iterator<
        Item = (
            EntityId,
            <<&'a mut ViewMut<'b, T> as IntoIter>::IntoIter as Iterator>::Item,
        ),
    >,
{
    for (id, mut x) in (&mut v).iter().with_id() {
        x.mutmut();
    }
}

But it triggers this issue rust-lang/rust#49601.
And I think it would also trigger the other one.
So in conclusion I don't know how to write a generic ViewMut iterator, sorry.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants