2016-04-27 5 views
2

Как объединить два объекта (оценки & человек) в один объект (объединенный). Я добрый борется с этим, поскольку я noobie с JavaScript, и я использую Meteor + Mongo combo.Как имитировать соединения SQL с помощью JavaScript

var scores = [ 
{person_id: "1", score_math: 9, score_biology: 9, score_chemistry: 9}, 
{person_id: "2", score_math: 9, score_biology: 8, score_chemistry: 9} 
]; 

var persons = [ 
{person_id: "1", person_name: "Bob", home_country: "Wakerly", age: 12}, 
{person_id: "2", person_name: "Arnie", home_country: "Templeton", age: 15}, 
{person_id: "3", person_name: "Steve", home_country: "Elberon", age: 10} 
]; 


var joined = [ 
{person_id: "1", person_name: "Bob", home_country: "Wakerly", score_math: 9, score_biology: 9, score_chemistry: 9}, 
{person_id: "2", person_name: "Arnie", home_country: "Templeton", score_math: 9, score_biology: 8, score_chemistry: 9}, 
{person_id: "3", person_name: "Steve", home_country: "Elberon", score_math: 0, score_biology: 0, score_chemistry: 0}]; 

ответ

1
var result = []; 
_.forEach(scores,function(score){ 
    var person = _.find(persons,{person_id:score.person_id}); 
    result.push(_.extend({}, score, person)); 
}); 

Это упрощенная версия. Я не обрабатываю значение, которое не найдено, и так далее. forEach будет проходить на весь счет. Затем I find первый собеседник, полагающий, что он уникален. Затем я объединю их, используя extend в новый объект.

Будьте осторожны с такими вещами, если у вас есть огромное количество наборов данных, эти задачи должны обрабатываться сзади. Если вам действительно нужно выполнить много соединений и вы можете изменить СУБД, вы можете обратиться за РСУБД, если она подходит больше.

1

попробовать:

var scores = [ 
 
{person_id: "1", score_math: 9, score_biology: 9, score_chemistry: 9}, 
 
{person_id: "2", score_math: 9, score_biology: 8, score_chemistry: 9} 
 
]; 
 

 
var persons = [ 
 
{person_id: "1", person_name: "Bob", home_country: "Wakerly", age: 12}, 
 
{person_id: "2", person_name: "Arnie", home_country: "Templeton", age: 15}, 
 
{person_id: "3", person_name: "Steve", home_country: "Elberon", age: 10} 
 
]; 
 
var joined = []; 
 
for (var i=0; i<persons.length; i++) { 
 
    var new_object = {}; 
 
    var found = false; 
 
    for (var j=0; j<scores.length; j++) { 
 
    if (scores[j].person_id == persons[i].person_id) { 
 
     found = true; 
 
     // copy all the values from score 
 
     for (var key in scores[j]) { 
 
     new_object[key] = scores[j][key]; 
 
     } 
 
     break; 
 
    } 
 
    } 
 
    if (!found) { 
 
    for (var key in scores[0]) { 
 
     new_object[key] = 0; 
 
    } 
 
    } 
 
    for (var key in persons[i]) { 
 
    new_object[key] = persons[i][key]; 
 
    } 
 
    joined.push(new_object); 
 
} 
 
document.body.innerHTML = '<pre>' + JSON.stringify(joined, true, 2) + '</pre>';

0

Вы можете сделать это с помощью основных массивов и объектов операций. Ниже код оптимизирован для этого.

var scores = [ 
 
{person_id: "1", score_math: 9, score_biology: 9, score_chemistry: 9}, 
 
{person_id: "2", score_math: 9, score_biology: 8, score_chemistry: 9} 
 
]; 
 

 
var persons = [ 
 
{person_id: "1", person_name: "Bob", home_country: "Wakerly", age: 12}, 
 
{person_id: "2", person_name: "Arnie", home_country: "Templeton", age: 15}, 
 
{person_id: "3", person_name: "Steve", home_country: "Elberon", age: 10} 
 
]; 
 

 
innerjoin=function(data1,data2,column){ 
 
    var joined=[]; 
 
    
 
    var d1len=data1.length; 
 
    var d2len=data2.length; 
 
    
 
    // Create dictionary from first array 
 
    var dict={}; 
 
    for(var i=0; i<d1len; i++){ 
 
    var item=data1[i]; 
 
    var key=item[column]; 
 
    var arr=dict[key]; 
 
    if(!arr){ 
 
     arr=dict[key]=[]; 
 
    } 
 
    arr.push(item); 
 
    } 
 
    
 
    // Join two arrays 
 
    for(var i=0; i<d2len; i++){ 
 
    var item=data2[i]; 
 
    var key=item[column]; 
 
    
 
    var arr=dict[key]; 
 
    if(!arr) continue; 
 
    for(var j=0,lenj=arr.length; j<lenj; j++) 
 
    { 
 
     joined.push(merge(item,arr[j])); 
 
    } 
 
    } 
 
    
 
    return joined; 
 
} 
 

 

 
merge=function(obj1,obj2){ 
 
    var res={}; 
 
    
 
    for(var key in obj1){ 
 
    if(obj1.hasOwnProperty(key)) res[key]=obj1[key]; 
 
    } 
 
    for(var key in obj2){ 
 
    if(obj2.hasOwnProperty(key)) res[key]=obj2[key]; 
 
    } 
 
    
 
    return res; 
 
} 
 

 
console.log(innerjoin(persons,scores,"person_id"));

2

Это предложение с временным объектом и некоторые методы массива в ванильным JS.

var scores = [{ person_id: "1", score_math: 9, score_biology: 9, score_chemistry: 9 }, { person_id: "2", score_math: 9, score_biology: 8, score_chemistry: 9 }], 
 
    persons = [{ person_id: "1", person_name: "Bob", home_country: "Wakerly", age: 12 }, { person_id: "2", person_name: "Arnie", home_country: "Templeton", age: 15 }, { person_id: "3", person_name: "Steve", home_country: "Elberon", age: 10 }], 
 
    joined = persons.map(function (a) { 
 
     function setProp(o) { Object.keys(o).forEach(function (k) { object[k] = o[k]; }); } 
 
     var object = {}; 
 
     setProp(a); 
 
     setProp(this[a.person_id] || { score_math: 0, score_biology: 0, score_chemistry: 0 }); 
 
     return object; 
 
    }, scores.reduce(function (r, a) { 
 
     r[a.person_id] = a; 
 
     return r; 
 
    }, Object.create(null))); 
 

 
document.write('<pre>' + JSON.stringify(joined, 0, 4) + '</pre>');

1

Вместо создания плоского объединенного объекта, я предлагаю вам создать новый объект, который содержит как человек и множество деталей.

Вы можете использовать на .map и на .filter функции для управления этим.

var scores = [ 
{person_id: "1", score_math: 9, score_biology: 9, score_chemistry: 9}, 
{person_id: "2", score_math: 9, score_biology: 8, score_chemistry: 9} 
]; 

var persons = [ 
{person_id: "1", person_name: "Bob", home_country: "Wakerly", age: 12}, 
{person_id: "2", person_name: "Arnie", home_country: "Templeton", age: 15}, 
{person_id: "3", person_name: "Steve", home_country: "Elberon", age: 10} 
]; 

//Function used in the .filter method. 'this' object is actually the person_id 
function getScoreByPersonId(score){ 
    return score.person_id == this; 
} 

//Basic students implementations. You can enrich the structure of the 'item' object depending on your requirements. 
var students = persons.map(function(p){ 
    var item = {}; 
    item['person'] = p; 
    item['score'] = scores.filter(getScoreByPersonId, p.person_id)[0] || {}; 
    return item; 

}); 
0

Вы можете сделать этот вид присоединяется легко с StrelkiJS:

var persons = new StrelkiJS.IndexedArray(); 
persons.loadArray([ 
    {id: "1", person_name: "Bob", home_country: "Wakerly", age: 12}, 
    {id: "2", person_name: "Arnie", home_country: "Templeton", age: 15}, 
    {id: "3", person_name: "Steve", home_country: "Elberon", age: 10} 
]); 

var scores = new StrelkiJS.IndexedArray(); 
scores.loadArray([ 
    {id: "1", score_math: 9, score_biology: 9, score_chemistry: 9}, 
    {id: "2", score_math: 9, score_biology: 8, score_chemistry: 9} 
]); 

var res = persons.query([{ 
    from_col:"id", 
    to_table: scores, 
    to_col: "id", 
    type: "outer" 
}]); 

Результат будет:

[ 
    [ 
    {"id":"1","person_name":"Bob","home_country":"Wakerly","age":12}, 
    {"id":"1","score_math":9,"score_biology":9,"score_chemistry":9} 
    ], 
    [ 
    {"id":"2","person_name":"Arnie","home_country":"Templeton","age":15}, 
    {"id":"2","score_math":9,"score_biology":8,"score_chemistry":9} 
    ], 
    [ 
    {"id":"3","person_name":"Steve","home_country":"Elberon","age":10}, 
    null 
    ] 
] 
Смежные вопросы