【问题标题】:Joins and Aggregates in Javascript ArraysJavascript 数组中的连接和聚合
【发布时间】:2013-02-23 18:20:06
【问题描述】:

我已经尝试了几个小时来使用 json.js 来做到这一点,但对于看起来简单的事情来说太过分了。我有这个示例数据:

    var hotels = [
        { id: 101, Name: "Hotel 101", WebFacilities: [8, 9, 10] },
        { id: 102, Name: "Hotel 101", WebFacilities: [8] },
        { id: 103, Name: "Hotel 101", WebFacilities: [8, 10] }
    ];

    var facilities = [
        { id: 8, Name: "Facility 8" },
        { id: 9, Name: "Facility 9" },
        { id: 10, Name: "Facility 10" }
    ];

我想得到这个:

    var selectedFacilities = [
        { id: 8, Name: "Facility 8", Count: 3 },
        { id: 9, Name: "Facility 9", Count: 1 },
        { id: 10, Name: "Facility 10", Count: 2 }
    ];

我该怎么做?

【问题讨论】:

    标签: javascript arrays linq.js


    【解决方案1】:

    所以看来您正在尝试计算每个设施的数量。

    这是使用 C# 编写查询的一种方法:

    var hotelFacilities =
        from hotel in hotels
        from id in hotel.WebFacilities
        group id by id;
    
    var query =
        from facility in facilities
        join g in hotelFacilities on facility.id equals g.Key
        select new
        {
            id = facility.id,
            Name = facility.Name,
            Count = g.Count(),
        };
    

    现在,如果您可以使用方法语法来描绘这一点,那么它几乎是对 linq.js 版本的 1:1 转换。

    请注意编译器转换上述内容的方式通常会将GroupBy() 调用包含在先前的SelectMany() 调用中。然而,这样编写将使编写 linq.js 等效查询更容易且不那么尴尬。

    var hotelFacilities = hotels
        .SelectMany(hotel => hotel.WebFacilities)
        .GroupBy(id => id);
    
    var query = facilities
        .Join(
            hotelFacilities,
            facility => facility.id,
            g => g.Key,
            (facility, g) => new
            {
                id = facility.id,
                Name = facility.Name,
                Count = g.Count(),
            }
        );
    

    和等效的 linq.js 查询。

    var hotelFacilities = Enumerable.From(hotels)
        .SelectMany("hotel => hotel.WebFacilities")
        .GroupBy("id => id")
        .ToArray();
    
    var query = Enumerable.From(facilities)
        .Join(
            hotelFacilities,
            "facility => facility.id",
            "g => g.Key()",
            "(facility, g) => { id: facility.id, Name: facility.Name, Count: g.Count() }"
        ).ToArray();
    

    【讨论】:

    • 优秀的答案。谢谢!
    【解决方案2】:

    使用这个:

    var selectedFacilities = facilities;
    
    for(var i = 0; i < facilities.length; i++) {
        for(var j = 0; j < hotels.length; j++) {
            if(hotels[j]["id"] == facilities[i]["id"]) {
                // Add data
                selectedFacilities[i]["Count"] = hotels[i]["WebFacilities"].length;
            } else {
                selectedFacilities[i]["Count"] = 0;
            }
        }
    
    }
    

    【讨论】:

    • 这似乎不对。我认为是我没有说清楚是我的错误。这个想法是获取每个设施的酒店数量。我已经更新了 ID,所以更清楚了
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2012-01-31
    • 2021-11-30
    • 1970-01-01
    • 2022-11-30
    • 2022-01-15
    相关资源
    最近更新 更多