用MongoDB实现MapReduce

来源:互联网 发布:数据分析ppt模板 编辑:程序博客网 时间:2024/04/29 15:37

MapReduce Google 2004年发布的一个软件框架,用于支持大规模数据的分布式计算,详情请看这里

MongoDB是一个开源的面向文档的 NoSQL数据库系统,使用 C++编写,详情请看这里

1.安装 MangoDB

首先请按照官方这个文档安装 MongoDB 数据库,在本文中,我们是在 Mac OS X下安装并测试无误。

我使用sudo port install mongodb命令来安装 MongoDB,唯一碰到的一个问题是 xcode的版本问题,升级到 xcode的最新版本就好了。

2.运行 MongoDB

启动 MongoDB是很简单的,只需要在终端窗口中执行 mogod即可。

默认 MongoDB是运行在 27017端口上,使用 /data/db作为默认目录来存放数据(我们已经在第一步就创建了这个目录)

如果你修改这些默认的配置,你可以通过命令行参数来进行修改:

mongod --port [your_port] --dbpath [your_db_file_path]

你需要确认的是数据目录必须已经存在并且在 mongodb首次启动时该目录下没有其他文件。

3.启动 MongoDB交互环境

我们可以启动 MongoDB交互环境来连接到 MongoDB服务器,并在命令行中直接运行 MongoDB命令。

在同一台机器上,你只需要简单的执行 mongo就可以进入交互环境,如果想要连接不同机器上的 MongoDB服务器,你可以使用下面的参数来指定目标服务器的IP地址和端口:

mongo [ip_address]:[port]

例如 : mongo localhost:4000

4.创建数据库

接下来在交互环境中执行下面命令来创建数据库:

use library

上述命令创建了一个名为 library的数据库。

然后我们可以通过下面的命令来查看刚创建的数据库,下面命令列出系统中所有的数据库:

show dbs;

你会注意到,你刚创建的数据库并没有列出来,这是因为 MongoDB只有在需要的时候才会创建数据库,因此你需要往数据库里添加点数据。

5.往数据库中插入数据

首先我们通过以下命令创建两本书:

> book1 = {name : "Understanding JAVA", pages : 100}
> book2 = {name : "Understanding JSON", pages : 200}

然后将这两本书保持到名为 books的集合中:

> db.books.save(book1)
> db.books.save(book2)

上述命令将在 library数据库中创建一个名为 books的集合(也就是SQL数据库中的表),下面命令将列出我们刚添加的两本书:

> db.books.find();

{ "_id" : ObjectId("4f365b1ed6d9d6de7c7ae4b1"), "name" : "Understanding JAVA", "pages" : 100 }
{ "_id" : ObjectId("4f365b28d6d9d6de7c7ae4b2"), "name" : "Understanding JSON", "pages" : 200 }

添加更多的记录:

> book = {name : "Understanding XML", pages : 300}
> db.books.save(book)
> book = {name : "Understanding Web Services", pages : 400}
> db.books.save(book)
> book = {name : "Understanding Axis2", pages : 150}
> db.books.save(book)

6.编写 Map函数

接下来我们编写一个搜索功能,用来查找超过250页的图书:

> var map = function() {

var category;

if ( this.pages >= 250 )

category = 'Big Books';

else

category = "Small Books";

emit(category, {name: this.name});

};

所返回的结果:

{"Big Books",[{name: "Understanding XML"}, {name : "Understanding Web Services"}]);
{"Small Books",[{name: "Understanding JAVA"}, {name : "Understanding JSON"},{name: "Understanding Axis2"}]);

7.编写 Reduce函数

> var reduce = function(key, values) {

var sum = 0;

values.forEach(function(doc) {

sum += 1;

});

return {books: sum};

};

8. books集合中运行 MapReduce

> var count = db.books.mapReduce(map, reduce, {out: "book_results"});

> db[count.result].find()

{ "_id" : "Big Books", "value" : { "books" : 2 } }

{ "_id" : "Small Books", "value" : { "books" : 3 } }

上述结果表明我们有两本大书和三本小书。

利用 MongoDB交互环境可以做任何事情,用 Java也一样,但是你需要下载一些必须的jar

下面是 Java的源码:

import com.mongodb.BasicDBObject;

import com.mongodb.DB;

import com.mongodb.DBCollection;

import com.mongodb.DBObject;

import com.mongodb.MapReduceCommand;

import com.mongodb.MapReduceOutput;

import com.mongodb.Mongo;

 

public class MongoClient {

 

 /**

 * @param args

 */

 public static void main(String[] args) {

 

 Mongo mongo;

 

 try {

  mongo = new Mongo("localhost", 27017);

  DB db = mongo.getDB("library");

 

  DBCollection books = db.getCollection("books");

 

  BasicDBObject book = new BasicDBObject();

  book.put("name", "Understanding JAVA");

  book.put("pages", 100);

  books.insert(book);

  

  book = new BasicDBObject(); 

  book.put("name", "Understanding JSON");

  book.put("pages", 200);

  books.insert(book);

  

  book = new BasicDBObject();

  book.put("name", "Understanding XML");

  book.put("pages", 300);

  books.insert(book);

  

  book = new BasicDBObject();

  book.put("name", "Understanding Web Services");

  book.put("pages", 400);

  books.insert(book);

 

  book = new BasicDBObject();

  book.put("name", "Understanding Axis2");

  book.put("pages", 150);

  books.insert(book);

  

  String map = "function() { "+

            "var category; " + 

            "if ( this.pages >= 250 ) "+ 

            "category = 'Big Books'; " +

            "else " +

            "category = 'Small Books'; "+ 

            "emit(category, {name: this.name});}";

  

  String reduce = "function(key, values) { " +

                           "var sum = 0; " +

                           "values.forEach(function(doc) { " +

                           "sum += 1; "+

                           "}); " +

                           "return {books: sum};} ";

  

  MapReduceCommand cmd = new MapReduceCommand(books, map, reduce,

    null, MapReduceCommand.OutputType.INLINE, null);

 

  MapReduceOutput out = books.mapReduce(cmd);

 

  for (DBObject o : out.results()) {

   System.out.println(o.toString());

  }

 } catch (Exception e) {

  // TODO Auto-generated catch block

  e.printStackTrace();

 }

 }

}

原创粉丝点击