使用Linq获取元组列表

本文关键字:列表 元组 获取 Linq 使用 | 更新日期: 2023-09-27 17:57:38

我有一个以时间点为中心的时间相关实体列表。例如,每个对象PricesAtTimeX包含关于苹果价格的信息,香蕉在一个特定时间点X的价格。

我想使用linq将那些转换为JSON,更以时间轴为中心的格式。例如,一个对象BananaPrices,它基本上由[日期,值]列表组成。

具体起点价格AtTimeX类

public class PricesAtTimeX
{
    public int ID { get; set; }
    public DateTime Date { get; set; }
    public int BananaPrice{ get; set; }
    public int ApplePrice{ get; set; }
}

我想从中得到什么:

[
    {
        "key": "BananaPrices",
        "values": [[date1, bananaPrice1], [date2, bananaPrice2] ... ],
    },
    {
        "key": "ApplePrices",
        "values": [[date1, applePrice1], [date2, applePrice2] ... ],
    }
]

我的问题是:如何使用Linq获得(int,int)列表?


我的第一次尝试是定义一个可以用来外壳数据的类:

public class dataLine
{
    public string key { get; set; }
    // first tuple-int would be date converted to javascript datetime
    public List<Tuple<int, int>> values { get; set; }
}

然后尝试用Linq:来填充

var result = from x in db.Prices
             select new List<dataLine>
             {
                 new dataLine() {
                     key = "ApplePrices",
                     values = ???
                 }
             };
return Json(result, JsonRequestBehavior.AllowGet);

另一种方法是将所有值打包到单独的列表中。。

var xValues = from x in db.Prices select new List<DateTime>() { x.Date };
var yBananas = from x in db.Prices select new List<int>() { x.BananaPrice};
var yApples = from x in db.Prices select new List<int>() { x.ApplePrice};

然后使用.Zip方法将每个价目表与日期列表合并

public List<Tuple<int, int>> TupleMe(List<int> list1, List<int> list2)
{
    return list1.Zip(list2, Tuple.Create).ToList();
}

如果有任何建议、暗示或想法,我将不胜感激!

使用Linq获取元组列表

一个简单的Select和使用object[]应该可以随心所欲。

通常,您会使用自定义类型KeyValuePairTupleDateBanana-/ApplePrice组合在一起(为了类型安全),但由于您无论如何都要创建JSON字符串,因此使用匿名类型和简单的object[]是最简单的方法。

var items = new []
{
    new PricesAtTimeX
    {
        ID = 1,
        Date = DateTime.Now.AddDays(-3),
        ApplePrice = 10,
        BananaPrice = 20
    },
    new PricesAtTimeX
    {
        ID = 1,
        Date = DateTime.Now.AddDays(-2),
        ApplePrice = 12,
        BananaPrice = 20
    },
    new PricesAtTimeX
    {
        ID = 1,
        Date = DateTime.Now.AddDays(-1),
        ApplePrice = 14,
        BananaPrice = 10
    },
    new PricesAtTimeX
    {
        ID = 1,
        Date = DateTime.Now,
        ApplePrice = 17,
        BananaPrice = 7
    },
};
// maybe cache 'items' if you're running LINQ against a database
// and if you're not wanting to hit the database multiple times.
var result = new[]
{
    new 
    {
        key = "BananaPrices",
        values = items.Select(i => new object[]{i.Date, i.BananaPrice})
    },
    new 
    {
        key = "ApplePrices",
        values = items.Select(i => new object[]{i.Date, i.ApplePrice})
    },
};
var json = JsonConvert.SerializeObject(result);

json现在(为了可读性而格式化):

[
 {"key":"BananaPrices","values":[["2014-04-06T13:39:01.109062+02:00",20],["2014-04-07T13:39:01.109062+02:00",20],["2014-04-08T13:39:01.109062+02:00",10],["2014-04-09T13:39:01.109062+02:00", 7]]},
 {"key":"ApplePrices" ,"values":[["2014-04-06T13:39:01.109062+02:00",10],["2014-04-07T13:39:01.109062+02:00",12],["2014-04-08T13:39:01.109062+02:00",14],["2014-04-09T13:39:01.109062+02:00",17]]}
]

尝试使用let来分离子查询中的查询逻辑,并将其应用于结果,例如:

var result = from x in db.Prices
             let t = (from p in db.Prices select new { x.Date, x.BananaPrice, x.ApplePrice }
             select new List<dataLine>
             {
                 new dataLine() {
                     key = "ApplePrices",
                     values = t1.Select(t => Tuple.Create(t.Date, t.BananaPrice))
                 }
             };