如何在Rust中共享功能?
现在,我想创建一个如何在Rust中共享功能?,rust,Rust,现在,我想创建一个Normal,它的行为几乎与向量完全相同,但我需要区分类型。例如,变换法线不同于变换向量。例如,您需要使用变换(逆)矩阵对其进行变换 现在我可以这样做: struct Vector { data: [f32; 2] } impl Vector { //many methods } 然后重新实现所有功能 struct Normal { v: Vector } 我想我也可以用它 不确定如何实现子范围的功能。例如,点积可能仅适用于法线和向量,而不适用于点
Normal
,它的行为几乎与向量
完全相同,但我需要区分类型。例如,变换法线不同于变换向量。例如,您需要使用变换(逆)矩阵对其进行变换
现在我可以这样做:
struct Vector {
data: [f32; 2]
}
impl Vector {
//many methods
}
然后重新实现所有功能
struct Normal {
v: Vector
}
我想我也可以用它
不确定如何实现子范围的功能。例如,点积可能仅适用于法线和向量,而不适用于点
是否可以表示特征边界的布尔表达式
impl Vector<NormalType> {..} // Normal specific stuff
trait-NormalTrait;
性状向量;
NormalType{}的impl NormalTrait
向量类型{}的impl vectorrait
向量的impl{
fn点(自身,其他:向量)->f32{..}
}
我的备选方案是什么?你的问题相当广泛,涉及很多话题。但是您的
PhantomData
想法可能是一个很好的解决方案。您可以为不同的泛型类型编写不同的impl
块。我在代码中添加了一些内容:
trait NormalTrait;
trait VectorTrait;
impl NormalTrait for NormalType {}
impl VectorTrait for VectorType {}
impl<T: PointTrait or VectorTrait> for Vector<T> {
fn dot(self, other: Vector<T>) -> f32 {..}
}
struct向量类型;
结构规范类型;
结构点类型;
结构向量{
数据:[f32;2],
_类型:幻影数据,
}
类型法线=向量;
类型点=向量;
//---这一行上面是旧代码--------------------
特征点{}
向量类型{}的impl Pointy
点类型{}的impl Pointy
//实现所有向量类型
impl向量{
fn new()->Self{
载体{
数据:[0.0,0.0],
_类型:幻影数据,
}
}
}
//“尖头”向量类型的impl
impl向量{
fn add(&mut self,other:Vector){}
fn变换(&mut self){/*标准矩阵乘法*/}
}
//法线的impl
impl向量{
fn变换(&mut-self){/*变换逆矩阵stuff*/}
}
fn main(){
设mut n=Normal::new();
设mut p=Point::new();
n、 transform();
p、 transform();
//n.add(Normal::new());//错误:
//在当前作用域中找不到类型为“Vector”的名为“add”的方法
p、 添加(Point::new());
}
是否可以表示特征边界的布尔表达式
impl Vector<NormalType> {..} // Normal specific stuff
没有(还没有)。但在这种情况下,您可以如上所示解决它:您创建一个新的trait(
Pointy
),并为“or”-条件中的类型实现它。然后你就被这种特质束缚住了。不需要幻影数据。只要用T
(我想)替换它就行了。类似于字节顺序是如何实现的。特征边界中的布尔表达式是否有RFC?@MaikKlein与所讨论的情况不完全相同,但我的答案无论如何会有很大变化。@Shepmaster不使用PhantomData
我们必须构造T
类型的对象,这有点问题。。。所以我们必须绑定T:Default
或任何东西。我想:P
trait NormalTrait;
trait VectorTrait;
impl NormalTrait for NormalType {}
impl VectorTrait for VectorType {}
impl<T: PointTrait or VectorTrait> for Vector<T> {
fn dot(self, other: Vector<T>) -> f32 {..}
}
struct VectorType;
struct NormalType;
struct PointType;
struct Vector<T = VectorType> {
data: [f32; 2],
_type: PhantomData<T>,
}
type Normal = Vector<NormalType>;
type Point = Vector<PointType>;
// --- above this line is old code --------------------
trait Pointy {}
impl Pointy for VectorType {}
impl Pointy for PointType {}
// implement for all vector types
impl<T> Vector<T> {
fn new() -> Self {
Vector {
data: [0.0, 0.0],
_type: PhantomData,
}
}
}
// impl for 'pointy' vector types
impl<T: Pointy> Vector<T> {
fn add<R>(&mut self, other: Vector<R>) {}
fn transform(&mut self) { /* standard matrix multiplication */ }
}
// impl for normals
impl Vector<NormalType> {
fn transform(&mut self) { /* tranposed inversed matrix stuff */ }
}
fn main() {
let mut n = Normal::new();
let mut p = Point::new();
n.transform();
p.transform();
// n.add(Normal::new()); // ERROR:
// no method named `add` found for type `Vector<NormalType>` in the current scope
p.add(Point::new());
}