gpt4 book ai didi

rust - 为什么我不能在模式匹配时使用常量,即使它实现了 PartialEq 和 Eq?

转载 作者:行者123 更新时间:2023-11-29 08:04:45 25 4
gpt4 key购买 nike

我想在模式匹配时使用常量 net::Ipv4Addr::LOCALHOST 过滤掉 IPv4 本地主机地址:

use get_if_addrs; // 0.5.3
use std::net;

fn main() -> std::io::Result<()> {
assert_eq!(
"127.0.0.1".parse::<net::Ipv4Addr>().unwrap(),
net::Ipv4Addr::LOCALHOST
);
{
let ifaces = get_if_addrs::get_if_addrs().unwrap();
for iface in ifaces {
match iface.addr {
get_if_addrs::IfAddr::V4(get_if_addrs::Ifv4Addr {
ip: _,
netmask: _,
broadcast: None,
}) => (),
get_if_addrs::IfAddr::V4(get_if_addrs::Ifv4Addr {
ip: net::Ipv4Addr::LOCALHOST,
netmask: _,
broadcast: _,
}) => (),
get_if_addrs::IfAddr::V4(addr) => println!("{:?}", addr),
get_if_addrs::IfAddr::V6(_) => (),
}
}
}
Ok(())
}

我得到一个错误

error: to use a constant of type `std::net::Ipv4Addr` in a pattern, `std::net::Ipv4Addr` must be annotated with `#[derive(PartialEq, Eq)]`
--> src/main.rs:19:25
|
19 | ip: net::Ipv4Addr::LOCALHOST,
| ^^^^^^^^^^^^^^^^^^^^^^^^

warning: unreachable pattern
--> src/main.rs:23:17
|
23 | get_if_addrs::IfAddr::V4(addr) => println!("{:?}", addr),
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
|
= note: #[warn(unreachable_patterns)] on by default

std::net::Ipv4Addr确实有 PartialEqEq 的实现,那么这个错误是什么意思?我该如何解决?

最佳答案

如错误消息所述:

must be annotated with #[derive(PartialEq, Eq)]

这是 not true for Ipv4Addr ,它手动实现它,而不是派生它。

相反,使用比赛后卫:

use get_if_addrs; // 0.5.3

fn main() -> std::io::Result<()> {
let ifaces = get_if_addrs::get_if_addrs().unwrap();
for iface in ifaces {
match iface.addr {
get_if_addrs::IfAddr::V4(get_if_addrs::Ifv4Addr {
broadcast: None, ..
}) => (),
get_if_addrs::IfAddr::V4(get_if_addrs::Ifv4Addr { ip, .. }) if ip.is_loopback() => (),
get_if_addrs::IfAddr::V4(addr) => println!("{:?}", addr),
get_if_addrs::IfAddr::V6(_) => (),
}
}

Ok(())
}

你也可以考虑引入一些嵌套:

use get_if_addrs::{IfAddr, Ifv4Addr}; // 0.5.3

fn main() -> std::io::Result<()> {
let ifaces = get_if_addrs::get_if_addrs().unwrap();
for iface in ifaces {
match iface.addr {
IfAddr::V4(addr) => match addr {
Ifv4Addr {
broadcast: None, ..
} => (),
Ifv4Addr { ip, .. } if ip.is_loopback() => (),
addr => println!("{:?}", addr),
},
IfAddr::V6(_) => (),
}
}

Ok(())
}

RFC 1445更多地解释了潜在的决定:

  • Introduce a feature-gated attribute #[structural_match] which can be applied to a struct or enum T to indicate that constants of type T can be used within patterns.
  • Have #[derive(Eq)] automatically apply this attribute to the struct or enum that it decorates. Automatically inserted attributes do not require use of feature-gate.
  • When expanding constants of struct or enum type into equivalent patterns, require that the struct or enum type is decorated with #[structural_match]. Constants of builtin types are always expanded.

The practical effect of these changes will be to prevent the use of constants in patterns unless the type of those constants is either a built-in type (like i32 or &str) or a user-defined constant for which Eq is derived (not merely implemented).

关于rust - 为什么我不能在模式匹配时使用常量,即使它实现了 PartialEq 和 Eq?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/55104576/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com