Warning: file_get_contents(/data/phpspider/zhask/data//catemap/7/rust/4.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Vector 如何将向量中的一个元素替换为基于原始元素的另一个元素 请考虑下面的程序(这是一个最小化的例子,所以不要挂断事实,我在这里做的事情可以用 HashMap 更好地实现): #[派生(PartialEq)] 枚举MyVariant{ 没有一个 一些价值, 其他价值观, 骨料(Vec) } impl-MyVariant{ 带有(self,其他:self)->self的pub fn{ 如果self==self::无{ 其他 }如果其他==Self::无,则为else{ 自己 }否则{ Self::聚合(vec![Self,other]) } } } fn添加变量(vec:&mut vec,id:u32,变量:MyVariant){ 如果让某些(项)=vec.iter_mut().find(|项|项.0==id){ *item=(id,item.1.with(variant)); }否则{ 向量推送((id,变量)); } } fn main(){ 让mut-vec:vec=vec::new(); 添加变量(&mut-vec,1,MyVariant::SomeValue); 添加变量(&mut-vec,2,MyVariant::None); 添加变量(&mut-vec,1,MyVariant::SomeOtherValue); }_Vector_Rust - Fatal编程技术网

Vector 如何将向量中的一个元素替换为基于原始元素的另一个元素 请考虑下面的程序(这是一个最小化的例子,所以不要挂断事实,我在这里做的事情可以用 HashMap 更好地实现): #[派生(PartialEq)] 枚举MyVariant{ 没有一个 一些价值, 其他价值观, 骨料(Vec) } impl-MyVariant{ 带有(self,其他:self)->self的pub fn{ 如果self==self::无{ 其他 }如果其他==Self::无,则为else{ 自己 }否则{ Self::聚合(vec![Self,other]) } } } fn添加变量(vec:&mut vec,id:u32,变量:MyVariant){ 如果让某些(项)=vec.iter_mut().find(|项|项.0==id){ *item=(id,item.1.with(variant)); }否则{ 向量推送((id,变量)); } } fn main(){ 让mut-vec:vec=vec::new(); 添加变量(&mut-vec,1,MyVariant::SomeValue); 添加变量(&mut-vec,2,MyVariant::None); 添加变量(&mut-vec,1,MyVariant::SomeOtherValue); }

Vector 如何将向量中的一个元素替换为基于原始元素的另一个元素 请考虑下面的程序(这是一个最小化的例子,所以不要挂断事实,我在这里做的事情可以用 HashMap 更好地实现): #[派生(PartialEq)] 枚举MyVariant{ 没有一个 一些价值, 其他价值观, 骨料(Vec) } impl-MyVariant{ 带有(self,其他:self)->self的pub fn{ 如果self==self::无{ 其他 }如果其他==Self::无,则为else{ 自己 }否则{ Self::聚合(vec![Self,other]) } } } fn添加变量(vec:&mut vec,id:u32,变量:MyVariant){ 如果让某些(项)=vec.iter_mut().find(|项|项.0==id){ *item=(id,item.1.with(variant)); }否则{ 向量推送((id,变量)); } } fn main(){ 让mut-vec:vec=vec::new(); 添加变量(&mut-vec,1,MyVariant::SomeValue); 添加变量(&mut-vec,2,MyVariant::None); 添加变量(&mut-vec,1,MyVariant::SomeOtherValue); },vector,rust,Vector,Rust,这将在*item=(id,item.1.with(variant))处失败,因为item是一个共享的可变引用,因此item.1不能移动到with()方法中。我试着使用一个指向向量的索引来获取一个引用,但这并不能解决根本的问题 基本上,我想要的是一个方法,它将临时将一个值移出可变向量,并用一个新的派生值替换它。可能是这样的: impl-Vec{ ///将“index”处的项替换为“replacer”生成的新项。 ///'replacer'将旧项作为参数接收。 fn替换_为(&mut self,索引

这将在
*item=(id,item.1.with(variant))
处失败,因为
item
是一个共享的可变引用,因此
item.1
不能移动到
with()
方法中。我试着使用一个指向向量的索引来获取一个引用,但这并不能解决根本的问题

基本上,我想要的是一个方法,它将临时将一个值移出可变向量,并用一个新的派生值替换它。可能是这样的:

impl-Vec{
///将“index”处的项替换为“replacer”生成的新项。
///'replacer'将旧项作为参数接收。
fn替换_为(&mut self,索引:usize,替换:fn(T)->T);
}
但我找不到像上面这样的方法,也找不到任何能达到同样目的的技术


我想我可能是从错误的角度看问题,有什么想法吗?谢谢

此代码应该可以工作。它与您的不同之处在于,它构造了一个临时占位符,然后使用
std::mem::swap
将其交换到
Vec
中,以便通过值传递实际值

#[derive(PartialEq)]
enum MyVariant {
    None,
    SomeValue,
    SomeOtherValue,
    Aggregate(Vec<MyVariant>)
}

impl MyVariant {
    pub fn with(self, other: Self) -> Self {
        if self == Self::None {
            other
        } else if other == Self::None {
            self
        } else {
            Self::Aggregate(vec![self, other])
        }
    }
}

fn add_variant(vec: &mut Vec<(u32, MyVariant)>, id: u32, variant: MyVariant) {
    if let Some(item) = vec.iter_mut().find(|item| item.0 == id) {
        let mut temp = (0, MyVariant::None); // create placeholder value
        std::mem::swap(item, &mut temp); // swap the placeholder in
        *item = (id, temp.1.with(variant)); // overwrite with real value
    } else {
        vec.push((id, variant));
    }
}

fn main() {
    let mut vec: Vec<(u32, MyVariant)> = Vec::new();
    add_variant(&mut vec, 1, MyVariant::SomeValue);
    add_variant(&mut vec, 2, MyVariant::None);
    add_variant(&mut vec, 1, MyVariant::SomeOtherValue);
}
#[派生(PartialEq)]
枚举MyVariant{
没有一个
一些价值,
其他价值观,
骨料(Vec)
}
impl-MyVariant{
带有(self,其他:self)->self的pub fn{
如果self==self::无{
其他
}如果其他==Self::无,则为else{
自己
}否则{
Self::聚合(vec![Self,other])
}
}
}
fn添加变量(vec:&mut vec,id:u32,变量:MyVariant){
如果让某些(项)=vec.iter_mut().find(|项|项.0==id){
让mut temp=(0,MyVariant::None);//创建占位符值
std::mem::swap(item,&mut temp);//在中交换占位符
*item=(id,temp.1.with(variant));//用实际值覆盖
}否则{
向量推送((id,变量));
}
}
fn main(){
让mut-vec:vec=vec::new();
添加变量(&mut-vec,1,MyVariant::SomeValue);
添加变量(&mut-vec,2,MyVariant::None);
添加变量(&mut-vec,1,MyVariant::SomeOtherValue);
}

此代码应该有效。它与您的不同之处在于,它构造了一个临时占位符,然后使用
std::mem::swap
将其交换到
Vec
中,以便通过值传递实际值

#[derive(PartialEq)]
enum MyVariant {
    None,
    SomeValue,
    SomeOtherValue,
    Aggregate(Vec<MyVariant>)
}

impl MyVariant {
    pub fn with(self, other: Self) -> Self {
        if self == Self::None {
            other
        } else if other == Self::None {
            self
        } else {
            Self::Aggregate(vec![self, other])
        }
    }
}

fn add_variant(vec: &mut Vec<(u32, MyVariant)>, id: u32, variant: MyVariant) {
    if let Some(item) = vec.iter_mut().find(|item| item.0 == id) {
        let mut temp = (0, MyVariant::None); // create placeholder value
        std::mem::swap(item, &mut temp); // swap the placeholder in
        *item = (id, temp.1.with(variant)); // overwrite with real value
    } else {
        vec.push((id, variant));
    }
}

fn main() {
    let mut vec: Vec<(u32, MyVariant)> = Vec::new();
    add_variant(&mut vec, 1, MyVariant::SomeValue);
    add_variant(&mut vec, 2, MyVariant::None);
    add_variant(&mut vec, 1, MyVariant::SomeOtherValue);
}
#[派生(PartialEq)]
枚举MyVariant{
没有一个
一些价值,
其他价值观,
骨料(Vec)
}
impl-MyVariant{
带有(self,其他:self)->self的pub fn{
如果self==self::无{
其他
}如果其他==Self::无,则为else{
自己
}否则{
Self::聚合(vec![Self,other])
}
}
}
fn添加变量(vec:&mut vec,id:u32,变量:MyVariant){
如果让某些(项)=vec.iter_mut().find(|项|项.0==id){
让mut temp=(0,MyVariant::None);//创建占位符值
std::mem::swap(item,&mut temp);//在中交换占位符
*item=(id,temp.1.with(variant));//用实际值覆盖
}否则{
向量推送((id,变量));
}
}
fn main(){
让mut-vec:vec=vec::new();
添加变量(&mut-vec,1,MyVariant::SomeValue);
添加变量(&mut-vec,2,MyVariant::None);
添加变量(&mut-vec,1,MyVariant::SomeOtherValue);
}

鉴于您无法复制或克隆
变体,并且
with
拥有所有权,您需要输入一个虚拟值,以避免出现单元化内存。您可以使用
std::mem::replace

fn add_variant(vec: &mut Vec<(u32, MyVariant)>, id: u32, variant: MyVariant) {
    if let Some(item) = vec.iter_mut().find(|item| item.0 == id) {
        let old_item = std::mem::replace(&mut item.1, MyVariant::None);
        item.1 = old_item.with(variant);
    } else {
        vec.push((id, variant));
    }
}
fn添加变量(vec:&mut-vec,id:u32,变量:MyVariant){
如果让某些(项)=vec.iter_mut().find(|项|项.0==id){
让old_item=std::mem::replace(&mut item.1,MyVariant::None);
项目1=旧项目,带有(变体);
}否则{
向量推送((id,变量));
}
}

鉴于您无法复制或克隆
变体,并且
with
拥有所有权,您需要输入一个虚拟值,以避免出现单元化内存。您可以使用
std::mem::replace

fn add_variant(vec: &mut Vec<(u32, MyVariant)>, id: u32, variant: MyVariant) {
    if let Some(item) = vec.iter_mut().find(|item| item.0 == id) {
        let old_item = std::mem::replace(&mut item.1, MyVariant::None);
        item.1 = old_item.with(variant);
    } else {
        vec.push((id, variant));
    }
}
fn添加变量(vec:&mut-vec,id:u32,变量:MyVariant){
如果让某些(项)=vec.iter_mut().find(|项|项.0==id){
让old_item=std::mem::replace(&mut item.1,MyVariant::None);
项目1=旧项目,带有(变体);
}否则{
向量推送((id,变量));
}
}
中有很多不错的选项,但您可以在结构实现本身中进行替换:

impl MyVariant {
    pub fn with_inplace(&mut self, other: Self) {
        if self == &Self::None {
            *self = other
        } else {
            if other != Self::None {
                let tmp = std::mem::replace(self, Self::None);
                *self = Self::Aggregate(vec![tmp, other]);
            }
        }
    }
}
然后在迭代中调用它:

if let Some(item) = vec.iter_mut().find(|item| item.0 == id) {
    item.1.with_inplace(variant);
} else {
    vec.push((id, variant));
}
中有很好的选项,但您可以在结构实现本身中进行替换:

impl MyVariant {
    pub fn with_inplace(&mut self, other: Self) {
        if self == &Self::None {
            *self = other
        } else {
            if other != Self::None {
                let tmp = std::mem::replace(self, Self::None);
                *self = Self::Aggregate(vec![tmp, other]);
            }
        }
    }
}
然后在迭代中调用它:

if let Some(item) = vec.iter_mut().find(|item| item.0 == id) {
    item.1.with_inplace(variant);
} else {
    vec.push((id, variant));
}

或者呢?这个变量没有默认值(虽然我想我可以添加它),但实际上我可以使用两个
std::mem::swap()
调用来解决它。我只是希望有一个更符合人体工程学的API…更新:正如彼得·霍尔的回答所示,我已经决定了