第一次看到/:以及:\这样的代码在别人的代码里,感觉很好奇,这是什么符号呢?
点进去看到方法的签名
def /:[B](z: B)(op: (B, A) => B): B = foldLeft(z)(op) def :\[B](z: B)(op: (A, B) => B): B = foldRight(z)(op)OK,原来是foldLeft和foldRight的简写
foldLeft和foldRight直接翻译来向左折叠,向右折叠。
先来看定义:
def foldLeft[B](z: B)(op: (B, A) => B): B = { var result = z this.seq foreach (x => result = op(result, x)) result }
在看到这个trait其实是TraversableOnce,可迭代的集合。
def seq: TraversableOnce[A]
比如一个val listA = List(1,2,3)
listA其实是实现了TraversableOnce这个trait的。
我们可以直接使用:
scala> listA.foldLeft(0)((sum,i)=>sum+i) res26: Int = 6
那么可以看出op这个函数返回值也需要是Int类型
可以看出
val result = z, 这里其实就是0,x=>result=op(result, x) , sum其实也是z
其实z就是返回值,this.seq在这里就是list,对list遍历,这里执行op函数。
这里我们执行的是sum+i,就是累加了1+2+3=6
def foldRight[B](z: B)(op: (A, B) => B): B = reversed.foldLeft(z)((x, y) => op(y, x))
// for internal use protected[this] def reversed = { var elems: List[A] = Nil self.seq foreach (elems ::= _) elems }内部使用的方法,意思就是
scala> ((1 to 5)).foldRight(100)((sum,i)=>sum-i) res48: Int = -97
scala> ((1 to 5)).foldRight(100)((i,sum)=>sum-i) res49: Int = 85
scala> (0/:(1 to 100))(_+_) res32: Int = 5050其实是等价于
scala> (1 to 100).foldLeft(0)(_+_) res33: Int = 5050
scala> ((1 to 5):\100)((i,sum)=> sum-i) res51: Int = 85