
お!頑張っているなという顔している柴犬です。
ここ数日、というか2週間ほど RUST のトレイト周辺の理解に苦しんでいましたが、ちょっと光が見えてきました。
トレイトのソースを読むのが一番いいようです。
そのお陰、今回の投稿ができました。
概要
構造体の大小比較したい場合、条件次第で次のコードで可能です。
#[derive(PartialEq, PartialOrd)]
struct Sline {
f0: u32,
f1: String,
f2: String,
}
// 構造体のメソッド
impl Sline {
fn new(f0: u32, f1: &str, f2: &str) -> Self {
Self {
f0: 0,
f1: f1.to_string(),
f2: f2.to_string(),
}
}
}
fn main() {
let s1 = Sline::new(1, "0234","15");
let s2 = Sline::new(5, "1234","13");
println!("{}", s1 > s2);
}
上のコードを Rust Playground で実行すると次のようになります。

しかし、大小の判定は構造体の要素順でしかならないなど制約があるため、これを任意にしてできるようにしてみました。
考えたコード
構造体の要素 f0 を無視して大小を比較するようにしてみました。
use std::cmp::Ordering;
// 構造体の定義
#[derive(Eq)]
struct Sline {
f0: u32,
f1: String,
f2: String,
}
// 構造体のメソッド
impl Sline {
fn new(f0: u32, f1: &str, f2: &str) -> Self {
Self {
f0: 0,
f1: f1.to_string(),
f2: f2.to_string(),
}
}
}
impl Ord for Sline {
fn cmp(&self, other: &Self) -> Ordering {
match (self.f1.cmp(&other.f1), self.f2.cmp(&other.f2)) {
(Ordering::Greater, _) => Ordering::Greater,
(Ordering::Equal, Ordering::Greater) => Ordering::Greater,
(Ordering::Equal, Ordering::Equal) => Ordering::Equal,
_ => Ordering::Less,
}
}
}
impl PartialOrd for Sline {
fn partial_cmp(&self, other: &Self) -> Option<Ordering> {
Some(self.cmp(other))
}
}
impl PartialEq for Sline {
fn eq(&self, other: &Self) -> bool {
self.f1 == other.f1 && self.f2 == other.f2
}
}
fn main() {
let s1 = Sline::new(1, "1234","12");
let s2 = Sline::new(5, "1234","11");
println!("{}", s1 > s2);
}
上のコードを Rust Playground で実行すると次のようになります。

要素 f0 を無視して大小を比較した結果になっています。
Ordering について
Ordering は、2 つの値を比較した結果を表す列挙型です。
pub enum Ordering {
Less,
Equal,
Greater,
}
例
let result = 1.cmp(&2);
result には Ordering::Less が格納されます。
let result = 1.cmp(&1);
result には Ordering::Equal が格納されます。
let result = 2.cmp(&1);
result には Ordering::Greater が格納されます。
変形
次の部分をいじれば要素の選択、比較順、昇順、降順を任意に変えれそうです。
impl Ord for Sline {
fn cmp(&self, other: &Self) -> Ordering {
match (self.f1.cmp(&other.f1), self.f2.cmp(&other.f2)) {
(Ordering::Greater, _) => Ordering::Greater,
(Ordering::Equal, Ordering::Greater) => Ordering::Greater,
(Ordering::Equal, Ordering::Equal) => Ordering::Equal,
_ => Ordering::Less,
}
}
}
// 略
impl PartialEq for Sline {
fn eq(&self, other: &Self) -> bool {
self.f1 == other.f1 && self.f2 == other.f2
}
}