我正在尝试按时间顺序获取最新的x条目。 目前我在做:
var query = db.OrderByDecending(x => x.date).Take(x).OrderBy(x => x.date)
从一个方向排序,限制然后在另一个方向排序似乎很疯狂。它不像我现在使用的那样导致我不眠之夜,我只是想知道是否有更好的方法......
答案 0 :(得分:4)
通过第二次OrderBy
调用,列表已经排序,但顺序错误。因此,您可以拨打Reverse
,这会更快。
var query = db.OrderByDescending(x => x.date).Take(x).Reverse();
答案 1 :(得分:0)
这取决于'db'实际上是什么。如果它是一个集合,那么SLaks的建议。另一方面,ff是一个SQL数据库,这是一个linq2sql查询或linq到EF然后实际上两个OrderBy更好。这就是SQL的全部内容:描述所需的结果,让数据库引擎找出最佳的访问路径和查询计划以满足您的请求。
答案 2 :(得分:0)
它需要某种流缓冲区数据结构,但您可以非常轻松地编写TakeEnd
方法。虽然在这种特殊情况下使用Reverse可能是一个更好的主意。
这可以让你做这样的事情:
var query = db.OrderBy(x => x.date).TakeEnd(x);
使用此代码:
public static class Ext
{
private class StreamBuffer<T> : IEnumerable<T>
{
private int head = 0;
private bool filled = false;
private T[] stream;
public int Size { get; private set; }
public StreamBuffer(int size)
{
Size = size;
stream = new T[Size];
}
public void Add(T item)
{
stream[head] = item;
head += 1;
if (head >= Size)
{
head = 0;
filled = true;
}
}
public IEnumerator<T> GetEnumerator()
{
int start = filled ? head : 0;
int size = filled ? Size : head;
for (int i = 0; i < size; i += 1)
{
int p = (start + i) % Size;
yield return stream[p];
}
}
System.Collections.IEnumerator System.Collections.IEnumerable.GetEnumerator()
{
return GetEnumerator();
}
}
public static IEnumerable<T> TakeEnd<T>(this IEnumerable<T> enumerable, int count)
{
StreamBuffer<T> buffer = new StreamBuffer<T>(count);
foreach (T t in enumerable)
{
buffer.Add(t);
}
return buffer;
}
}