zoukankan      html  css  js  c++  java
  • Linq学习之路(07) 使用Linq进行参数化编程step by step

    我们在程序中往往需要添加过滤器的功能,检索数据的时候希望按照某些条件进行筛选或者排序,解决方案有很多种,比如拼SQL语句或者进行参数化编程。拼过滤条件是最低级最不安全的一种解决方案,不能很好的表现出面向对象编程的思想,正好本人最近在研究Linq,那么今天本人就使用Linq进行参数化编程,数据源还是参考我前面写的那些文章。

    给大家看一下UI:

     

      

    这里我们希望根据Title检索关键字,PageCount主要是想过滤掉那些不满足条件的Objects,SortOrder主要就是指定按照什么条件进行排序,有升序也有降序。

    主要界面就是这样,好吧,下面我们就开始如何一步一步实现这些功能:

    step1:初始换窗体

      这里我主要讲一下PageCount这个下拉框的初始化,我们设置下拉列表中每个项的显示的名字和与其对应的值,为了让界面变得友好,用户一眼就看出来是什么意思,所以我这里用了KeyValuePair来保存Key/Value,Key是给用户看的,而Value是给我们程序员看的,我们根据Value进行相应的操作。附上代码:

     cmbCountFilter.DisplayMember = "Key";
     cmbCountFilter.ValueMember = "Value";
     cmbCountFilter.DataSource = new KeyValuePair<String, int?>[] 
     {
         new KeyValuePair<String, int?>("any", null),
         new KeyValuePair<String, int?>("at least 100", 100),
         new KeyValuePair<String, int?>("at least 200", 200),
         new KeyValuePair<String, int?>("at least 300", 300)
     };

    另外,我们还要简单的讲一下用于显示检索结果的控件DataGridView控件,由于我们想让他显示我们自定义的元素,所以我们需要将DataGridView控件的AutoGenerateColumns属性值设置为false,这样我们就能让该控件显示我们自定义的列了,给你也给出代码:

           //这里我们只想显示自定义的三列:Title,Publisher,PageCount,
                //所以我们要把AutoGenerateColumns属性设为false
                dataGridView1.AutoGenerateColumns = false;
                dataGridView1.Columns.Clear();
                dataGridView1.Columns.Add(
                    new DataGridViewTextBoxColumn() { DataPropertyName = "Title", HeaderText = "Title" });
                dataGridView1.Columns.Add(
                    new DataGridViewTextBoxColumn() { DataPropertyName = "PageCount", HeaderText = "Pages" });
                dataGridView1.Columns.Add(
                    new DataGridViewTextBoxColumn() { DataPropertyName = "Publisher", HeaderText = "Publisher" });

    初始化工作我们就做的差不多了,下面开始我们的第二步:

    step2:自定义条件检索QueryByCondition

      大多数情况下,检索的条件会很多,如果每个条件都写一个方法,那么会大大的增加我们的代码量,而且方法重用的可能性不大,为了构建重用度非常好的方法,这里我们使用参数化编程,提高方法的重用度,代码量也惊人的变少,也是面向对象编程的初衷。

            /// <summary>
            /// 自定义条件检索
            /// </summary>
            /// <typeparam name="TSortKey">排序规则</typeparam>
            /// <param name="minPageCount">最小页码</param>
            /// <param name="titleFilter">标题过滤条件</param>
            /// <param name="sortSelector">排序条件</param>
            /// <param name="ascending">是否升序</param>
            public IEnumerable<Book> QueryByCondition<TSortKey>(int? minPageCount, string titleFilter, Func<Book, TSortKey> sortSelector, Boolean ascending)
            {
                IEnumerable<Book> books;
    
                books = SampleData.Books;
                if (minPageCount.HasValue)
                {
                    books = books.Where(book => book.PageCount >= minPageCount);
                }
                if (!String.IsNullOrEmpty(titleFilter))
                {
                    books = books.Where(book => book.Title.Contains(titleFilter));
                }
                if (sortSelector != null)
                {
                    if (ascending)
                    {
                        books = books.OrderBy(sortSelector);
                    }
                    else
                    {
                        books = books.OrderByDescending(sortSelector);
                    }
                }
    
                return books;
            }

    上面这段代码就是我们这个demo里面最核心的代码,我们根据传进来的这些参数进行判断检索,得到我们想要的那些数据。

    step3:根据我们在UI界面选择的条件检索我们期望的数据:

            /// <summary>
            /// 数据绑定
            /// </summary>
            public IEnumerable<Book> LoadData()
            {
                IEnumerable<Book> books = null;
    
                int? minPageCount;
                string titleFilter;
    
                minPageCount = (int?)cmbCountFilter.SelectedValue;
                titleFilter = txtTitleFilter.Text;
    
                switch (cmbSortOrder.SelectedIndex)
                {
                    case 0:
                        books =
                            QueryByCondition(minPageCount, titleFilter, book => book.Title, true);
                        break;
                    case 1:
                        books =
                            QueryByCondition(minPageCount, titleFilter, book => book.Title, false);
                        break;
                    case 2:
                        books =
                            QueryByCondition(minPageCount, titleFilter, book => book.Publisher.Name, true);
                        break;
                    case 3:
                        books =
                            QueryByCondition(minPageCount, titleFilter, book => book.Publisher.Name, false);
                        break;
                    case 4:
                        books =
                            QueryByCondition(minPageCount, titleFilter, book => book.PageCount, true);
                        break;
                    case 5:
                        books =
                            QueryByCondition(minPageCount, titleFilter, book => book.PageCount, false);
                        break;
                    default:
                        books =
                            QueryByCondition<Object>(minPageCount, titleFilter, null, true);
                        break;
                }
    
                //这里将检索到的books转换为List列表非常重要
                //因为Linq中对数据的检索存在Derfferd Query
                //如果这里没有加上ToList()方法的话,在UI层我们是不会得到结果的
                return books.ToList();
            }

    这段代码主要是根据我们选择的过滤条件和排序规则进行判断,然后传入相应的参数调用QueryByCondition方法。

    step4:最后一步,在btn_click事件中调用我们的LoadData方法:

            /// <summary>
            /// 按钮点击事件
            /// </summary>
            /// <param name="sender"></param>
            /// <param name="e"></param>
            private void btnSearch_Click(object sender, EventArgs e)
            {
                dataGridView1.DataSource = LoadData();
            }

    好了大功告成了,我们来看看我们的成果:

    1、按关键字检索:

      

    2、按最小页码检索:

      

    3、按排序规则检索:

      

    4、组合查询:

      

    5、默认查询:

      

    ok,这篇文章就讲到这里,let's make oop develop better!!!

    姓名:王卯东 英文名:Michael QQ:942352461 Email:armdong@163.com 主要研究方向:javascript,require.js;
  • 相关阅读:
    Atitit 经济学常见的流派 古典主义与凯恩斯主义
    Atitit 学习方法 体系化学习方法 Excel 科目,分类,专业 三级分类。。 知识点。。 课程就是每一个知识点的详细化。。 比如经济学 类别 专业 xx概论知识点 3、金
    atiitt it学科体系化 体系树与知识点概念大总结.xlsx
    Atitit 减少财政支出普通人如何蹭政府补贴措施 attilax大总结.docx
    Atitit 信用管理概论 attilax学习心得
    Atitit.月度计划日程表 每月流程表v5
    Atitit 企业6大职能 attilax总结
    Atitit 常见每日流程日程日常工作.docx v8 ver ampm imp 签到 am y 天气情况检查 am y 晨会,每天或者隔天 am 每日计划(项目计划,日计划等。 am
    Atitit 财政赤字解决方案
    Atitit 建设自己的财政体系 attilax总结 1.1. 收入理论 2 1.2. 收入分类 2 1.3. 2 1.4. 非货币收入 2 1.5. 2 1.6. 降低期望 2 1.7.
  • 原文地址:https://www.cnblogs.com/ARMdong/p/linqparameterizedfunc.html
Copyright © 2011-2022 走看看