问题描述
考虑下面的C ++模板类:
模板< class T>
class Point2
{
Point2(T x,T y):
x(x),
y(y)
{}
T x;
T y;
Point2< T> operator +(Point< T> const& other)const
{
return Point< T>(x + other.x,y + other.y);
}
T sumComponents()const {return x + y; }
}
Point2< Double> p0(12.3,45.6)
Point2< Double> p1(12.3,45.6)
Point2< Double> p = p1 + p2
Double d = p1.sumComponents()
我想写这样的东西:
case class Point2 [T](x:T,y:T){
def +()Point2 [T]:= x + y
def sumComponents()T:= x + y
}
或(因为编译有问题),
trait可添加[T] {//需要T支持+操作
def +(that:T):T
}
case class Point2 [T def +()Point2 [T]:= x + y
def sumComponents()T:= x + y
}
这同样存在问题,因为我不能要求Double扩展Addable。
实现上述的惯用方法是什么? Scala呢?
对于C ++模板程序员来说,理解scala中泛型极限的正确方法是什么? (为什么不能在scala中执行此操作?例如,是因为泛型是在实例化之前编译的吗?)
我创建了一个库。您可以使用该库创建C ++风格的模板,避免复杂隐式
s。
import com.thoughtworks.template
case class Point2 [T](x:T,y:T){
@template def +(rhs:Point2 [_])= Point2(x + rhs.x,y + rhs.y)
@template def sumComponents()= x + y
}
println(Point2(1,3).sumComponents()) //输出:4
println(Point2(1,3)+ Point2(100,200))//输出:Point2(101,203)
请注意,您甚至可以使用不同的组件类型加上两个 Point2
s。
println(Point2(1.5,0.3)+ Point2(100,200))//输出:Point2(101.5,200.3)
即使嵌套 Point2
:
<$ p (点2(0.1,0.2),点2(1.0,2.0))点数2(点2(10.1,20.2),点2(101.0,202.0))
println )+ Point2(Point2(10,20),Point2(100,200)))
因为 @template
函数是将在调用站点内联的代码模板。
I'm coming from C++ and trying to wrap my head around scala's type system.
Consider the following C++ template class:
template<class T>
class Point2
{
Point2( T x, T y ) :
x(x),
y(y)
{}
T x;
T y;
Point2<T> operator+( Point<T> const& other ) const
{
return Point<T>(x+other.x, y+other.y);
}
T sumComponents() const { return x+y; }
}
Point2<Double> p0(12.3, 45.6)
Point2<Double> p1(12.3, 45.6)
Point2<Double> p = p1+p2
Double d = p1.sumComponents()
I'm finding I want to write something like this:
case class Point2[ T ] (x:T, y:T) {
def +() Point2[T]: = x+y
def sumComponents() T: = x+y
}
or, (because the compile has problems with this),
trait Addable[T] { // Require T supports the + operatory
def +( that:T ):T
}
case class Point2[ T<:Addable[T] ] (x:T, y:T) {
def +() Point2[T]: = x+y
def sumComponents() T: = x+y
}
which is similarly problematic because I can't require Double to extend Addable.
Generally, I'm finding it scala's type system works with a set of constraints that I don't quite understand.
What's the idiomatic way of implementing the above in scala?
And what's the right way for C++ template programmers to understand the limits of generics in scala? (why can't I do this in scala? e.g. Is it because generics are compiled before being instaniated?)
I created a library template.scala. You can use the library to create C++ flavored templates, avoiding complicated implicit
s.
import com.thoughtworks.template
case class Point2[T](x:T, y:T) {
@template def +(rhs: Point2[_]) = Point2(x + rhs.x, y + rhs.y)
@template def sumComponents() = x + y
}
println(Point2(1, 3).sumComponents()) // Output: 4
println(Point2(1, 3) + Point2(100, 200)) // Output: Point2(101,203)
Note that you can even plus two Point2
s with different component types.
println(Point2(1.5, 0.3) + Point2(100, 200)) // Output: Point2(101.5,200.3)
Even nested Point2
:
// Output: Point2(Point2(10.1,20.2),Point2(101.0,202.0))
println(Point2(Point2(0.1, 0.2), Point2(1.0, 2.0)) + Point2(Point2(10, 20), Point2(100, 200)))
It works because @template
functions are code templates that will inline at the call site.
这篇关于scala是否提供类似C ++模板的东西?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!