2011-07-15 14 views
3

パート1:私は年齢とGPAを排除する必要がmongoDbのクエリとグループ化?

{ 
    sname : "", 
    studentId: "123" 
} 

:それから、2つだけのキーを取得しようとしている

{ 
    sname : "", 
    studentId: "123" 
    age: "", 
    gpa: "", 
} 

はイム:

私は(学生)のコレクションを持っています名前とstudentIdだけを持つようにするにはどうしたらいいですか?

パート2:私はとなってしまいますので、一致/正しいstudentIdで(その1)で、前のキーを組み合わせることが必要

{ 
    subjectName : "Math" 
    studentId : "123" 
    teacherName: "" 
} 

それから私は、「対象」のコレクションを持っています

{ 
    sname : "", 
    studentId: "123", 
    subjectName : "Math" 

} 

どうすれば結果を得ることができるのでしょうか?私はグループとmapReduceについて読んでみましたが、明確な例は見つけられませんでした。

答えて

4

あなたがこれを行うことができ、あなたの最初の質問に答えるために:

db.student.find({}, {"sname":1, "studentId":1}); 

{最初}という点では、この場合には、コレクション全体を含ん制限クエリ、です。後半では、キーを返すかどうかによって1または0のキーが指定されます。しかし、単一のクエリでincludeとexcludesを混在させないでください。特別な場合を除いて、mongoはそれを受け入れません。

2番目の質問は難しくなります。あなたが求めているのは、参加であり、モンゴはそれをサポートしていません。 studentIdに2つのコレクションを接続する方法はありません。あなたはあなたが望むすべての生徒を見つける必要がありますし、それらのstudentIdを使用して、すべての一致する科目を見つける必要があります。次に、あなた自身のコードで2つの結果をマージする必要があります。使用しているドライバによってこれを行うことができます。あるいは、シェル自体のjavascriptでこれを行うこともできますが、いずれにしても、あなた自身のコードとマージする必要があります。

編集: ここでは、出力を「out」というコレクションに出力するシェルでこれを行う方法の例を示します。

db.student.find({}, {"sname":1, "studentId":1}).forEach(
    function (st) { 
    db.subject.find({"studentId":st.studentId}, {"subjectName":1}).forEach(
     function (sub) { 
     db.out.insert({"sname":st.sname, "studentId":st.studentId, "subjectName":sub.subjectName}); 
     } 
    ); 
    } 
); 

これは、多くの場合、すべてのことを変更するデータがない場合は、あなただけの「アウト」コレクションをドロップすると、このシェルスクリプトを定期的に再作成することができます。次に、あなたのコードは "out"から直接問い合わせることができます。データが頻繁に変更される場合は、コード内でこのマージを実行したいと思うでしょう。

「学生」コレクションに「サブジェクト」データを含めるか、またはその逆も可能です。これにより、よりmongodbにやさしい構造になります。この結合問題に頻繁に遭遇すると、mongoが行く方法ではなく、リレーショナルデータベースがあなたのニーズに適しているかもしれません。

+1

あなたはまた減らすために[オペレータで$](http://www.mongodb.org/display/DOCS/Advanced+Queries#AdvancedQueries-%24in)を使用することができます:学生の書類と一緒にそれを取得クエリの数'out'テーブルを生成するために必要です。これは、負荷が高い場合、またはラウンドトリップ時間が多数の学生の要因となる可能性のあるネットワークを照会する場合に特に重要です。 – dcrosta

1

モンゴのfind()オペレータは、あなたが含まれたりの結果から

チェックアウトField Selectionドキュメントでの詳細は特定のフィールドを除外することができます。あなたがいずれかを行うことができます:一緒にあなたの学生と件名を関連付けるため

db.users.find({}, { 'sname': 1, 'studentId': 1 }); 
db.users.find({}, { 'age': 0, 'gpa': 0 }); 

、あなたは可能性のいずれかのように、学生が個別に持っている科目のルックアップ:各学生に

db.subjects.find({ studentId: 123 }); 

または埋め込み対象データを、そして

{ 
    sname : "Roland Browning", 
    studentId: "123" 
    age: 14, 
    gpa: "B", 
    subjects: [ { name : "French", teacher: "Mr Bronson" }, ... ] 
} 
関連する問題