首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >从MySQL查询生成Mongo查询

问从MySQL查询生成Mongo查询
EN

Stack Overflow用户
提问于 2013-03-08 10:09:52
回答 2查看 421关注 0票数 0

我一直在使用以下MySQL命令从日志数据构建热图。但是,我有一个存储在Mongo数据库中的新数据集,并且我需要运行相同的命令。

代码语言:javascript
复制
 select concat(a.packages '&' b.packages) "Concurrent Packages",
 count(*) "Count"
 from data a
 cross join data b
 where a.packages<b.packages and a.jobID=b.jobID
 group by a.packages, b.packages
 order by a.packages, b.packages;

请记住,表a和b在查询之前并不存在。但是,它们是从数据表的packages列创建的,数据表的jobID字段是我要检查匹配的字段。换句话说,如果两个包在同一个作业中,我希望在并发使用计数中添加一个条目。如何在Mongo中生成类似的查询?

EN

回答 2

Stack Overflow用户

发布于 2013-04-02 09:52:34

这不是不同文档的“连接”;它是one文档中的一个操作,可以在MongoDB中完成。

代码语言:javascript
复制
You have a SQL TABLE "data" like this:
  JobID   TEXT,
  package TEXT

将其存储在MongoDB中的最佳方式是一个名为"data“的集合,每个JobID包含一个文档,该文档包含一组包:

代码语言:javascript
复制
{
    _id: <JobID>,
    packages: [
        "packageA",
        "packageB",
        ....
    ]
}

注意:您还可以在MongoDB中将数据表实现为一个文档,其中包含一个作业数组,每个作业包含一个包数组。不建议这样做,因为您可能会达到16MB的文档大小限制,并且不同的查询(尚未)很好地支持嵌套数组-如果您还想将数据用于其他目的

现在,如何得到这样的结果呢?

代码语言:javascript
复制
{ pair: [ "packageA", "packageB" ], count: 20 },
{ pair: [ "packageA", "packageC" ], count: 11 },
...

由于MongoDB中没有内置的两个数组的“交叉联接”,因此您必须在mapReduce()的映射函数中对其进行编程,将每对包作为键发出:

代码语言:javascript
复制
mapf = function () {
    that = this;
    this.packages.forEach( function( p1 ) {
        that.packages.forEach( function( p2 ) {
            if ( p1 < p2 ) {
                key = { "pair": [ p1, p2 ] };
                emit( key, 1 );
            };
        });
    });
};

注意:如果对packages数组进行了排序,则可以对此进行优化

reduce函数只不过是对每个键的计数器求和:

代码语言:javascript
复制
reducef = function( key, values ) {
    count = 0;
    values.forEach( function( value ) { count += value } );
    return count;
};

因此,对于这个示例集合:

代码语言:javascript
复制
> db.data.find()
{ "_id" : "Job01", "packages" : [ "pA", "pB", "pC" ] }
{ "_id" : "Job02", "packages" : [ "pA", "pC" ] }
{ "_id" : "Job03", "packages" : [ "pA", "pB", "pD", "pE" ] }

we get the following result:

> db.data.mapReduce(
...     mapf,
...     reducef,
...     { out: 'pairs' }
... );
{
    "result" : "pairs",
    "timeMillis" : 443,
    "counts" : {
        "input" : 3,
        "emit" : 10,
        "reduce" : 2,
        "output" : 8
    },
    "ok" : 1,
}
> db.pairs.find()
{ "_id" : { "pair" : [ "pA", "pB" ] }, "value" : 2 }
{ "_id" : { "pair" : [ "pA", "pC" ] }, "value" : 2 }
{ "_id" : { "pair" : [ "pA", "pD" ] }, "value" : 1 }
{ "_id" : { "pair" : [ "pA", "pE" ] }, "value" : 1 }
{ "_id" : { "pair" : [ "pB", "pC" ] }, "value" : 1 }
{ "_id" : { "pair" : [ "pB", "pD" ] }, "value" : 1 }
{ "_id" : { "pair" : [ "pB", "pE" ] }, "value" : 1 }
{ "_id" : { "pair" : [ "pD", "pE" ] }, "value" : 1 }

有关mapReduce consult的更多信息,请访问:http://docs.mongodb.org/manual/reference/method/db.collection.mapReduce/和http://docs.mongodb.org/manual/applications/map-reduce/

票数 2
EN

Stack Overflow用户

发布于 2013-03-08 10:15:48

你不能。Mongo不做连接。从SQL切换到Mongo要比迁移查询复杂得多。

通常,您将在同一记录中包含所有相关信息(而不是标准化信息并使用连接选择它)。去正规化!

票数 1
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/15285513

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档