实现三个集合的笛卡儿积。支持函数式编程的语言可以通过flatMap实现
Scala:
val c1 = Set("A", "B", "C")
val c2 = Set("2", "3", "5", "9")
val c3 = Set("甲", "乙", "丙", "丁")
val collection = c1.flatMap(x => c2.flatMap(y => c3.map(z => Tuple3(x, y, z))))
collection.foreach(t => println(s"${t._1}:${t._2}:${t._3}"))
Ruby:
# -*- coding: UTF-8 -*-
require('set')
c1 = Set.new ["A", "B", "C"]
c2 = Set.new ["2", "3", "5", "9"]
c3 = Set.new ["甲", "乙", "丙", "丁"]
collection = c1.flat_map {|x|c2.flat_map {|y|c3.map{|z|"#{x}:#{y}:#{z}"}}}
collection.each { |line| puts line }
从上面的代码可以看出,Scala和Ruby的表达方式高度一致。
而java除了代码看起来多一些之外,表达方式上实际同Scala和Ruby没有本质差别。
Java 8:
import java.util.HashSet;
import java.util.List;
import java.util.Set;
import static java.lang.System.out;
import static java.util.Arrays.asList;
import static java.util.stream.Collectors.toList;
public class Cartesian {
public static void main(String[] args) {
Set c1 = new HashSet<>(asList("A", "B", "C"));
Set c2 = new HashSet<>(asList("2", "3", "5", "9"));
Set c3 = new HashSet<>(asList("甲", "乙", "丙", "丁"));
List collect = c1.stream()
.flatMap(x -> c2.stream()
.flatMap(y -> c3.stream()
.map(z -> Tuple3.newTuple(x, y, z))))
.collect(toList());
collect.forEach(out::println);
}
}
class Tuple3 {
private final T _1;
private final T _2;
private final T _3;
public static Tuple3 newTuple(T _1, T _2, T _3) {
return new Tuple3(_1, _2, _3);
}
private Tuple3(T _1, T _2, T _3) {
this._1 = _1;
this._2 = _2;
this._3 = _3;
}
public T _1() {
return _1;
}
public T _2() {
return _2;
}
public T _3() {
return _3;
}
@Override
public String toString() {
return String.format("%s:%s:%S", _1, _2, _3);
}
}
Python 2.x:
在Python中,可以通过列表推导实现
[(x, y, z) for x in c1 for y in c2 for z in c3]
实际上很多其他语言中比较复杂的操作在python都会以一种简洁、通用、甚至是无趣的方式实现,这正应了那句话:python是工程,而不是艺术。
# coding=utf-8
if __name__ == '__main__':
c1 = ("A", "B", "C")
c2 = ("2", "3", "5", "9")
c3 = (u"甲", u"乙", u"丙", u"丁")
cartesian = [(x, y, z) for x in c1 for y in c2 for z in c3]
for a, b, c in cartesian:
print "{a}:{b}:{c}".format(a=a, b=b, c=c.encode("utf-8"))
print len(cartesian)