2017-11-27 13 views
0

내 데이터 집합에 집계를 만들어서 .Net 응용 프로그램에있는 책 모음의 특정 태그에 대한 총 개수를 얻고 싶습니다.집계 프레임 워크의 패싯 사용 C#

다음 도서 클래스가 있습니다.

public class Book 
{ 
    public string Id { get; set; } 

    public string Name { get; set; } 

    [BsonDictionaryOptions(DictionaryRepresentation.Document)] 
    public Dictionary<string, string> Tags { get; set; } 
} 

데이터가 저장되면 MongoDB에 다음 형식으로 저장됩니다.

{ 
    "_id" : ObjectId("574325a36fdc967af03766dc"), 
    "Name" : "My First Book", 
    "Tags" : { 
     "Edition" : "First", 
     "Type" : "HardBack", 
     "Published" : "2017", 
    } 
} 

나는 MongoDB를 직접면을 사용하고 그리고 난 다음 쿼리를 사용하여 원하는 결과를 얻을 수 있어요 : 나는에 이상이 전송 드릴 수 없습니다 그러나

db.{myCollection}.aggregate(
    [ 
     { 
      $match: { 
       "Name" : "SearchValue" 
      } 
     }, 
     { 
      $facet: { 
       "categorizedByTags" : [ 
        { 
         $project : 
         { 
         Tags: { $objectToArray: "$Tags" } 
         } 
        }, 
        { $unwind : "$Tags"}, 
        { $sortByCount : "$Tags"} 
        ] 

      } 
     }, 
    ] 
); 

을 Mongo 용 .NET C# 드라이버. .NET C# 드라이버를 사용하여이 작업을 수행하려면 어떻게해야합니까?

편집 - 나는 궁극적으로 같은 출판사, 저자 등의 측면 책 목록 페이지의 일부로 책의 다른 속성에 DB를 조회하고자하는 것, 페이지 등 ... $면의 따라서 사용을 계산 ,이 일을하는 더 좋은 방법이 없다면?

답변

1

개인적으로는 최초의 장소에 $facet의 목적을 패배 한 파이프 라인 ...

다음은 간단있어 더 나은 ($facet 하나를 생성합니다 확장에만 했으므로 여기 $facet를 사용하지 것이다 잠재적으로 대량의 단일 문서). 우리는 때문에 다른을 필요로면을 사용하여 계획

var collection = new MongoClient().GetDatabase("test").GetCollection<Book>("test"); 

var project = PipelineStageDefinitionBuilder.Project<Book, BsonDocument>("{Tags: { $objectToArray: \"$Tags\" }}"); 
var unwind = PipelineStageDefinitionBuilder.Unwind<BsonDocument, BsonDocument>("Tags"); 
var sortByCount = PipelineStageDefinitionBuilder.SortByCount<BsonDocument, BsonDocument>("$Tags"); 

var pipeline = PipelineDefinition<Book, AggregateSortByCountResult<BsonDocument>>.Create(new IPipelineStageDefinition[] { project, unwind, sortByCount }); 

// string based alternative version 
//var pipeline = PipelineDefinition<Book, BsonDocument>.Create(
// "{ $project :{ Tags: { $objectToArray: \"$Tags\" } } }", 
// "{ $unwind : \"$Tags\" }", 
// "{ $sortByCount : \"$Tags\" }"); 

var facetPipeline = AggregateFacet.Create("categorizedByTags", pipeline); 

var aggregation = collection.Aggregate().Match(b => b.Name == "My First Book").Facet(facetPipeline); 

var output = aggregation.Single().Facets.ToJson(new JsonWriterSettings { Indent = true }); 

Console.WriteLine(output); 
+0

: 패싯을 사용하여 버전을 여기

var collection = new MongoClient().GetDatabase("test").GetCollection<Book>("test"); var pipeline = collection.Aggregate() .Match(b => b.Name == "My First Book") .Project("{Tags: { $objectToArray: \"$Tags\" }}") .Unwind("Tags") .SortByCount<BsonDocument>("$Tags"); var output = pipeline.ToList().ToJson(new JsonWriterSettings {Indent = true}); Console.WriteLine(output); 

의 다음과 같이

db.collection.aggregate([ { $match: { "Name" : "My First Book" } }, { $project: { "Tags": { $objectToArray: "$Tags" } } }, { $unwind: "$Tags" }, { $sortByCount: "$Tags" }, { $group: { // not really needed unless you need to have all results in one single document "_id": null, "categorizedByTags": { $push: "$$ROOT" } } }, { $project: { // not really needed, either: remove _id field "_id": 0 } }]) 

이는 C# 드라이버를 사용하여 작성 될 수있다 게시자, 작성자 등 다른 속성에 대한 쿼리 (예제를 단순화하기 위해 이전 질문에서 언급하지 않음) 기존 집계를 변경하려고합니다. i n 패싯을 사용하여 우리의 서적 목록 페이지에서 우리의 측면 탐색을위한 DB 호출의 총량을 줄이는 프로젝트. –

+0

@ Adzy_12 : $ facet 부분을 설명하는 업데이트 된 답변을 보셨습니까? – dnickless

+0

이것은 내가 찾고있는 것으로 보인다. 나는 당신의 대답을 수락 된 것으로 표시 할 것입니다, 고마워요. –