Поскольку вы не предоставили формат образца документа (объекта), примите его в качестве образца коллекции под названием 'story' .
{ "_id" : ObjectId("4eafd693627b738f69f8f1e3"), "body" : "There was a king", "author" : "tom" }
{ "_id" : ObjectId("4eafd69c627b738f69f8f1e4"), "body" : "There was a queen", "author" : "tom" }
{ "_id" : ObjectId("4eafd72c627b738f69f8f1e5"), "body" : "There was a queen", "author" : "tom" }
{ "_id" : ObjectId("4eafd74e627b738f69f8f1e6"), "body" : "There was a jack", "author" : "tom" }
{ "_id" : ObjectId("4eafd785627b738f69f8f1e7"), "body" : "There was a humpty and dumpty . Humtpy was tall . Dumpty was short .", "author" : "jane" }
{ "_id" : ObjectId("4eafd7cc627b738f69f8f1e8"), "body" : "There was a cat called Mini . Mini was clever cat . ", "author" : "jane" }
. Для данного набора данных вы можете использоватьследующий код JavaScript, чтобы добраться до вашего решения.Коллекция " авторы_unigrams " содержит результат.Весь код должен быть запущен с использованием консоли mongo (http://www.mongodb.org/display/DOCS/mongo+-+The+Interactive+Shell).
Сначала , нам нужно пометить все новые документы, которые снова попали в 'story' Мы делаем это, используя следующую команду: он добавит новый атрибут с именем «mr_status» в каждый документ и присвоит значение «inprocess». Позже мы увидим, что операция map-Reduce будет принимать только те документы, которые имеютзначение "inprocess" для поля "mr_status". Таким образом, мы можем избежать повторного рассмотрения всех документов для операции уменьшения карты, которые уже рассматривались в любой из предыдущих попыток, что делает операцию эффективной в соответствии с запросом.
db.stories.update({mr_status:{$exists:false}},{$set:{mr_status:"inprocess"}},false,true);
Второй , мы определяем обе функции map () и Reduce () .
var map = function() {
uniqueWords = function (words){
var arrWords = words.split(" ");
var arrNewWords = [];
var seenWords = {};
for(var i=0;i<arrWords.length;i++) {
if (!seenWords[arrWords[i]]) {
seenWords[arrWords[i]]=true;
arrNewWords.push(arrWords[i]);
}
}
return arrNewWords;
}
var unigrams = uniqueWords(this.body) ;
emit(this.author, {unigrams:unigrams});
};
var reduce = function(key,values){
Array.prototype.uniqueMerge = function( a ) {
for ( var nonDuplicates = [], i = 0, l = a.length; i<l; ++i ) {
if ( this.indexOf( a[i] ) === -1 ) {
nonDuplicates.push( a[i] );
}
}
return this.concat( nonDuplicates )
};
unigrams = [];
values.forEach(function(i){
unigrams = unigrams.uniqueMerge(i.unigrams);
});
return { unigrams:unigrams};
};
Третий , мы фактически запускаем функцию уменьшения карты.
var result = db.stories.mapReduce( map,
reduce,
{query:{author:{$exists:true},mr_status:"inprocess"},
out: {reduce:"authors_unigrams"}
});
Четвертый , мы помечаем все записи, которые были рассмотрены для уменьшения карты в последнем запуске, как обработанные установкой "mr_status "как" обработано ".
db.stories.update({mr_status:"inprocess"},{$set:{mr_status:"processed"}},false,true);
Опционально , вы можете увидеть коллекцию результатов "hors_unigrams" , запустив следующую команду.
db.authors_unigrams.find();