enum Result {
Ok(String),
Err(String),
}
T
/E
表示泛型
enum Result<T, E> {
Ok(T),
Err(E),
}
// 非泛型,直接类型
struct Point {
x: i32,
y: i32,
}
// T 泛型: T: i32/i64/f32
struct Point<T> {
x: T,
y: T,
}
enum List<T> {
Nil,
Cons(T, Box<List<T>>),
}
enum Result<T, E> {
Ok(T),
Err(E),
}
impl<T, E> Result<T, E> {
fn is_ok(&self) -> bool {
match *self {
Ok(_) => true,
Err(_) => false,
}
}
}
error: Could not compile `cargo8I6mnS`.
#[derive(Debug)]
struct Point {
x: i32,
y: i32,
}
struct Line {
from: Point,
to: Point,
}
// Trait 类似于 Java 的接口或 Haskell 的 typeclass
trait PrettyPrint {
fn format(&self) -> String;
}
// 实现 Trait
impl PrettyPrint for Point {
fn format(&self) -> String {
format!("({},{})", self.x, self.y)
}
}
impl PrettyPrint for Line {
fn format(&self) -> String {
format!("[{}->{}]", self.from.format(), self.to.format())
}
}
fn main() {
let p0 = Point { x: 0, y: 0 };
println!("p0 = {}", p0.format());
let p1 = Point { x: 1, y: 1 };
let line = Line { from: p0, to: p1 };
println!("line = {}", line.format());
// let p1 = Point{x:1, y:0};
// println!("{}", p0.equals(p1));
}
p0 = (0,0) line = [(0,0)->(1,1)]
// 范围限定
fn cloning_machine<T: Clone>(t: T) -> (T, T) {
(t.clone(), t.clone())
}
fn cloning_machine<T>(t: T) -> (T, T) where T: Clone {
(t.clone(), t.clone())
}
// Trait 类似于 Java 的接口或 Haskell 的 typeclass
trait PrettyPrint {
fn format(&self) -> String;
}
// 使用标准库中的 Result
// #[derive(Debug)]
// enum Result<T, E> {
// Ok(T),
// Err(E),
// }
impl<T, E> PrettyPrint for Result<T, E>
where
T: PrettyPrint,
E: PrettyPrint,
{
fn format(&self) -> String {
match self {
Ok(t) => format!("Ok({})", t.format()),
Err(e) => format!("Err({})", e.format()),
}
}
}
trait Equals {
fn equals(&self, other: &Self) -> bool;
}
impl<T, E> Equals for Result<T, E>
where
T: Equals,
E: Equals,
{
fn equals(&self, other: &Self) -> bool {
match (self, other) {
(Ok(t1), Ok(t2)) => t1.equals(&t2),
(Err(e1), Err(e2)) => e1.equals(&e2),
_ => false,
}
}
}
fn main() {
let ok1:Result::<String, String> = Result::Ok("1".to_string());
let ok2 = Result::Ok::<String, String>("1".to_string());
println!("{:?}", ok1);
println!("{:?}", ok2);
// println!("{:?}", ok1.equals(&ok2));
}
Ok("1") Ok("1")
trait Parent {
fn foo(&self) {
//
}
}
trait Child: Parent {
fn bar(&self) {
self.foo();
//
}
}
trait AAA {
fn foo(&self) -> bool {
true
}
}
- 通过
#[derive(...)]
指定需要派生的 trait - 如果有继承关系,需要同时派生其父 trait
#[derive(Eq, PartialEq, Debug)]
enum Result<T, E> {
Ok<T>,
Err<E>,
}
#[derive(Clone)]
struct Foo {
x: i32,
}
#[derive(Clone)]
struct Bar {
x: Foo,
}
- Clone, Copy
- Debug
- Default
- Eq, PartialEq
- Hash
- Ord, PartialOrd
- 图 graph
- 节点集 node
- 边集 edge
trait Graph<N, E> {
fn edges(&self, n: &N) -> Vec<E>;
}
// 求图中两个节点的距离
fn distance<N, E, G: Graph<N, E>>(graph: &G, start: &N, end: &N) -> u32 {
1
}
改进版
trait Graph {
type N;
type E;
fn edges(&self, n: &Self::N) -> Vec<Self::E>;
}
struct MyGraph {}
struct MyNode {}
struct MyEdge {}
impl Graph for MyGraph {
type N = MyNode;
type E = MyEdge;
fn edges(&self, n: &MyNode) -> Vec<MyEdge> {
vec![]
}
}
关联类型
- struct MyGraph {}
- struct MyNode {}
- struct MyEdge {}
trait Foo {
fn bar(&self) -> bool;
}
impl Foo for i32 {
fn bar(&self) -> bool {
true
}
}
println!("{}", (-123i32).bar());
true
use std::fmt::{self, Display};
struct Point {
x: i32,
y: i32,
}
impl Display for Point {
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
write!(f, "Pt({},{})", self.x, self.y)
}
}
let p0 = Point { x: 0, y: 0 };
println!("{}", p0); // Display
// println!("{:?}", p0); // Debug
Pt(0,0)
trait Draw {
fn draw(&self) -> String;
}
impl Draw for u32 {
fn draw(&self) -> String {
format!("u32: {}", self)
}
}
impl Draw for i32 {
fn draw(&self) -> String {
format!("i32: {}", self)
}
}
fn draw1(x: &dyn Draw) {
x.draw();
}
fn draw2(x: Box<dyn Draw>) {
x.draw();
}
fn main() {
let a = 10i32;
let b = 11u32;
draw1(&a);
draw1(&b);
draw2(Box::new(a));
draw2(Box::new(b));
}
trait Foo { fn bar(&self); }
impl Foo for String {
fn bar(&self) {
println!("String[{}]", self);
}
}
impl Foo for i32 {
fn bar(&self) {
println!("i32[{}]", self);
}
}
fn blah<T>(x: T) where T: Foo {
x.bar()
}
let s = "xxx".to_string();
let i = 12;
blah(s);
blah(i);
String[xxx] i32[12]
trait Foo { fn bar(&self); }
impl Foo for char {
fn bar(&self) {
println!("char[{}]", self);
}
}
impl Foo for i32 {
fn bar(&self) {
println!("i32[{}]", self);
}
}
fn use_foo(f: &dyn Foo) {
match *f { // 编译时出错: error[E0308]: mismatched types
198 => println!("198 aaa"),
'c' => println!("See?"),
_ => println!("Something else..."),
}
}
use_foo(&'c'); // 这里发生强制转换,抹除了类型信息
use_foo(&198i32);
error: Could not compile `cargo45Rxl1`.