目的
- 使用Spark中GraphX自带的ShortestPaths求下图的最短路径
- GraphX自带的ShortestPaths只能求无权图的最短路径,相当于每条边的权重等于1
- 过段时间会研究一下加权图_(:з」∠)_
无权无向图
环境
- IntelliJ IDEA + Maven + Spark_2.1.1
- Scala_2.11.0
过程
新建工程的详细步骤这里不写,具体请参考这里
具体代码:
import org.apache.spark.graphx.Graph
import org.apache.spark.{SparkConf, SparkContext}
import org.apache.spark.graphx.lib.ShortestPaths
/**
* Created by give on 17-5-8.
*/
object getShortestPaths {
def main(args: Array[String]): Unit = {
val conf = new SparkConf()
.setAppName("getShortestPaths")
.setMaster("local") // 指定Master
.setSparkHome("/usr/lib/spark/spark-2.1.1-bin-hadoop2.7")
// setSparkHome指向安装spark的地址,视环境而定
val sc = new SparkContext(conf)
// 构造无向图的边,将一条无向边用两条有向边表示
val edgeSeq = Seq((1,2), (1,5), (2,3), (2,5), (3,4), (4,5), (4,6)).flatMap{
case e => Seq(e, e.swap)
}
// 将每条边对应的两个点的ID从Int类型转换成Long类型,并创建RDD
// GraphX中图的点ID规定是Long类型
val edges = sc.parallelize(edgeSeq).map{case (v1:Int, v2:Int) => (v1.toLong, v2.toLong)}
// 从边RDD创建图graph
val graph = Graph.fromEdgeTuples(edges, 1)
// landmarks指明需要用哪几个点作为最短路径的终点,注意ID是Long类型
val landmarks = Seq(1,2,3).map(_.toLong)
// 运行ShortestPaths,求最短路径
val results = ShortestPaths.run(graph, landmarks)
// 输出结果,每个点到landmarks里的点的最短路径
results.vertices.collect.foreach(println)
}
}
- 输出结果
(4,Map(3 -> 1, 2 -> 2, 1 -> 2))
(1,Map(1 -> 0, 2 -> 1, 3 -> 2))
(6,Map(3 -> 2, 2 -> 3, 1 -> 3))
(3,Map(3 -> 0, 2 -> 1, 1 -> 2))
(5,Map(1 -> 1, 2 -> 1, 3 -> 2))
(2,Map(2 -> 0, 1 -> 1, 3 -> 1))
- 解释
(4,Map(3 -> 1, 2 -> 2, 1 -> 2))
// 4到3的最短路径是1,4到2的最短路径是2,4到1的最短路径是2
- 成功啦( ̄︶ ̄)