zoukankan      html  css  js  c++  java
  • IEnumerable的一些基本方法 补充

    接上一篇,我们发现两表连接方式默认为内连接,而我们在SQL中常用到的左连接没有封装方法。换句话说,微软放弃两表左连或右连的这种做法(只有在2个表都存在值时,这样的连接才有意义)。

    如果要实现表的左连接,就不能调用他现有的封装方法了,可以用LINQ来实现。

    var joinTable = (from left in table1.AsEnumerable()
                        join right in table2.AsEnumerable()
                        on left["ID"].ToString() equals right["ID"].ToString() into newTable
                        from right in newTable.DefaultIfEmpty()
                        select new
                        {
                            LeftID = left["ID"].ToString(),
                            RightID = right != null ? right["ID"].ToString() : default(string),
                            LeftName = left["Name"].ToString(),
                            RightName = right != null ? right["Name"].ToString() : default(string)
                        }).ToList();
    joinTable.ForEach(t => Console.WriteLine("{0}	{1}	{2}	{3}", t.LeftID, t.RightID, t.LeftName, t.RightName));

    功能是实现了,但是这样又要憋死一群强迫症患者,非要用Join封装方法来实现这个功能。

    那我们就来手动封装一个左连接方法吧。

    public static IEnumerable<Result> LeftJoin<TOuter, TInner, TKey, Result>(
        this IEnumerable<TOuter> outer
        , IEnumerable<TInner> inner
        , Func<TOuter, TKey> outerKeySelector
        , Func<TInner, TKey> innerKeySelector
        , Func<TOuter, TInner, Result> resultSelector
        , IEqualityComparer<TKey> comparer)
    {
        if (outer == null)
            throw new ArgumentException("outer");
    
        if (inner == null)
            throw new ArgumentException("inner");
    
        if (outerKeySelector == null)
            throw new ArgumentException("outerKeySelector");
    
        if (innerKeySelector == null)
            throw new ArgumentException("innerKeySelector");
    
        if (resultSelector == null)
            throw new ArgumentException("resultSelector");
    
        return LeftJoinImpl(outer, inner, outerKeySelector, innerKeySelector, resultSelector, comparer ?? EqualityComparer<TKey>.Default);
    }
    
    static IEnumerable<Result> LeftJoinImpl<TOuter, TInner, TKey, Result>(
        IEnumerable<TOuter> outer, IEnumerable<TInner> inner
        , Func<TOuter, TKey> outerKeySelector
        , Func<TInner, TKey> innerKeySelector
        , Func<TOuter, TInner, Result> resultSelector
        , IEqualityComparer<TKey> comparer)
    {
        var innerLookup = inner.ToLookup(innerKeySelector, comparer);
    
        foreach (var outerElment in outer)
        {
            var outerKey = outerKeySelector(outerElment);
            var innerElements = innerLookup[outerKey];
    
            if (innerElements.Any())
                foreach (var innerElement in innerElements)
                    yield return resultSelector(outerElment, innerElement);
            else
                yield return resultSelector(outerElment, default(TInner));
        }
    }

    PS:以上这段代码转载自stackoverflow.com

    var joinTable = table1.AsEnumerable().LeftJoin(table2.AsEnumerable(),
        left => left["ID"].ToString(),
        right => right["ID"].ToString(),
        (left, right) => new
        {
            LeftID = left["ID"].ToString(),
            RightID = right != null ? right["ID"].ToString() : default(string),
            LeftName = left["Name"].ToString(),
            RightName = right != null ? right["Name"].ToString() : default(string)
        }, null).ToList();
    joinTable.ForEach(t => Console.WriteLine("{0}	{1}	{2}	{3}", t.LeftID, t.RightID, t.LeftName, t.RightName));

    是不是和之前的Join方法一样,这样用起来很方便了吧。

  • 相关阅读:
    axios基本用法
    Iframe父子窗口之间的跨域事件调用和传值
    js 比较两个日期的大小
    小程序webview实践
    小程序入口构造工具&二维码测试工具
    小程序无限层级路由方案
    TypeScript基础类型,类实例和函数类型声明
    小程序多业务线融合【完整分包业务接入】
    浅谈React16框架
    CSS Modules 与 scoped 的不一样
  • 原文地址:https://www.cnblogs.com/TanSea/p/IEnumerable-Additional.html
Copyright © 2011-2022 走看看