Asp.net 可以在GridView上进行自定义排序吗

Asp.net 可以在GridView上进行自定义排序吗,asp.net,gridview,sorting,Asp.net,Gridview,Sorting,我需要对需要复杂排序的GridView(不是DataGridView,这不是同一件事),我不知道如何进行排序。我有两列,一列包含日期,另一列包含优先级 如果日期小于或等于今天的日期。我想先按优先顺序订购,然后按日期订购。如果日期大于今天的日期,我想先按日期排序,然后按优先级排序 假设今天是2010年1月13日,以这种方式订购的一些数据可能如下所示 date priority Explanation ----------- -------- ---------------

我需要对需要复杂排序的GridView(不是DataGridView,这不是同一件事),我不知道如何进行排序。我有两列,一列包含日期,另一列包含优先级

如果日期小于或等于今天的日期。我想先按优先顺序订购,然后按日期订购。如果日期大于今天的日期,我想先按日期排序,然后按优先级排序

假设今天是2010年1月13日,以这种方式订购的一些数据可能如下所示

   date       priority  Explanation
-----------   --------  --------------------------------------------
2010-jan-13      3      This comes first because it has the higer priority of all items whith a date <= today
2010-jan-12      2      Since this items and the next have the same priority they're ordered by date
2010-jan-13      2
2010-jan-14      5      This item and the followings have date > today, so they are ordered by date then by priority.
2010-jan-14      0
2010-jan-15      5
2010-jan-16      5
日期优先级说明
-----------   --------  --------------------------------------------

2010年1月13日这是第一个,因为它在所有项目中具有更高的优先级,其中数据的排序过程使用数据源的排序过程。 要手动对数据进行排序,请创建实现IBindingListView的类,实现您想要的排序方法,并将该类用作DataGridView中的数据源

假设您使用的是一个数据源,并且每个元素都是一个类(而不是一个datarow),那么您可以实现与类的IComparable。它添加了CompareTo方法,您可以在该方法中决定每个元素之间的比较方式

class DatePriority: IComparable
{
    private DateTime date;
    public DateTime Date
    {
        get { return date; }
    }
    private int priority;
    public int Priority
    {
        get { return priority; }
    }

    public DatePriority(DateTime date, int priority)
    {
        this.date = date;
        this.priority = priority;
    }

    public int CompareTo(object obj)
    {
        if (obj is DatePriority)
        {
            DatePriority comparedDatePriority = obj as DatePriority;

            // Comparison logic
            // If the compared elements are today or before today, order by priority in descending order. Same priorities are ordered by date in ascending order
            // If the compared elements are for the future, order by date in ascending order. Same dates are order by priority in descending order
            if ((this.Date <= DateTime.Today && comparedDatePriority.Date <= DateTime.Today))
            {
                if (Priority == comparedDatePriority.Priority)
                    return Date.CompareTo(comparedDatePriority.Date);
                else
                    return -Priority.CompareTo(comparedDatePriority.Priority);
            }
            else
            {                    
                if (Date == comparedDatePriority.date)
                    return -Priority.CompareTo(comparedDatePriority.Priority); // Descending order
                else
                    return Date.CompareTo(comparedDatePriority.Date);
            }
        }
        throw new ArgumentException("Not a DatePriority");
    }
}    
类日期优先级:i可比较
{
私人日期时间日期;
公共日期时间日期
{
获取{返回日期;}
}
私人优先权;
公共整数优先级
{
获取{返回优先级;}
}
公共日期优先级(日期时间日期,整数优先级)
{
this.date=日期;
优先权=优先权;
}
公共整数比较(对象对象对象)
{
如果(obj是日期优先级)
{
DatePriority comparedDatePriority=obj作为DatePriority;
//比较逻辑
//如果比较的元素是今天或今天之前,则按优先级降序排列。相同的优先级按日期升序排列
//如果比较的元素是未来的,则按日期升序排列。相同的日期按优先级降序排列

if((this.Date您需要对数据源而不是GridView进行排序。(告诉我们您的数据源,我们可以提供帮助。它是DataTable、SqlDataSource、business objects吗?)

从中的GridView Web服务器控件中排序数据

自定义排序 如果默认排序行为不足以满足您的要求,您可以自定义网格的排序行为。自定义排序的基本技术是处理排序事件。在处理程序中,您可以执行以下操作:

  • 自定义传递给数据源控件的排序表达式。默认情况下,排序表达式是单个列的名称。可以在事件处理程序中修改排序表达式。例如,如果要按两列排序,可以创建同时包含这两列的排序表达式。然后,可以传递修改后的排序表达式到数据源控件。有关更多信息,请参阅GridViewSortEventArgs..::.SortExpression属性

  • 创建自己的排序逻辑。例如,如果您使用的数据源不支持排序,您可以在自己的代码中执行排序,然后将网格绑定到排序数据。

排序示例(未测试且未使用LINQ[故意]) 将oDataSet设置为DataSet=GatherDataSet() Dim oDataTable As DataTable=oDataSet.Tables(0) Dim oSort1作为新数据视图(oDataTable,“日期>2010/01/13”,“日期,优先级”,DataViewRowState.CurrentRows)
Dim oSort2作为新的数据视图(oDataTable,“Date是的,您可以这样做。下面是如何做到的

假设您有一个从BusinessLayer方法调用记录的GridView,我将以UserManager为例作为业务层代理类

    [DataObjectAttribute()]
    public static class UserManager
    {
        [DataObjectMethod(DataObjectMethodType.Select, true)]
        public static UserCollection GetUsers()
        {
            return UserDB.GetAll();
        }

        [DataObjectMethod(DataObjectMethodType.Select, false)]
        public static UserCollection GetUsers(string sortExpression)
        {
            UserCollection users = UserDB.GetAll();
            users.Sort(new EntityComparer<User>(sortExpression));
            return users;
        }
    }
[DataObjectAttribute()]
公共静态类用户管理器
{
[DataObjectMethod(DataObjectMethodType.Select,true)]
公共静态UserCollection GetUsers()
{
返回UserDB.GetAll();
}
[DataObjectMethod(DataObjectMethodType.Select,false)]
公共静态UserCollection GetUsers(string-sortExpression)
{
UserCollection users=UserDB.GetAll();
Sort(新的EntityComparer(sortExpression));
返回用户;
}
}
在重载的GetUsers方法中查看这行代码

users.Sort(new EntityComparer<User>(sortExpression));
users.Sort(新的EntityComparer(sortExpression));
我已经为我的业务对象编写了一个通用比较器实现。EntityComparer只是一个实现IComparer接口的通用类。您可以编写自己的比较器实现[实现IComparer接口],并将其作为上面的代码调用

下面是我的GridView的外观

         <asp:GridView ID="GridView1" runat="server" AutoGenerateColumns="False" 
            DataSourceID="ObjectDataSource1">
            <Columns>
                <asp:BoundField DataField="Id" HeaderText="Id" SortExpression="Id" />
                <asp:BoundField DataField="UserName" HeaderText="UserName" 
                    SortExpression="UserName" />
                <asp:BoundField DataField="Password" HeaderText="Password" 
                    SortExpression="Password" />
                <asp:BoundField DataField="Name" HeaderText="Name" SortExpression="Name" />
                <asp:BoundField DataField="Email" HeaderText="Email" SortExpression="Email" />
                <asp:BoundField DataField="CompanyName" HeaderText="CompanyName" 
                    SortExpression="CompanyName" />
            </Columns>
        </asp:GridView>
        <asp:ObjectDataSource ID="ObjectDataSource1" runat="server" 
            OldValuesParameterFormatString="original_{0}" SelectMethod="GetUsers" 
            TypeName="FilePark.BusinessLayer.UserManager"></asp:ObjectDataSource>


另请注意,GridView将在回发时传递sortExpression并调用重载方法。

如果这是网格的默认视图,我将在数据访问代码中将列表排序,然后再将其绑定到GridView。@AMissico,数据源是一个表,是否有手动排序数据表的方法?@AMissico,谢谢,这肯定会成功的解决我的问题。我接受了这个答案。
         <asp:GridView ID="GridView1" runat="server" AutoGenerateColumns="False" 
            DataSourceID="ObjectDataSource1">
            <Columns>
                <asp:BoundField DataField="Id" HeaderText="Id" SortExpression="Id" />
                <asp:BoundField DataField="UserName" HeaderText="UserName" 
                    SortExpression="UserName" />
                <asp:BoundField DataField="Password" HeaderText="Password" 
                    SortExpression="Password" />
                <asp:BoundField DataField="Name" HeaderText="Name" SortExpression="Name" />
                <asp:BoundField DataField="Email" HeaderText="Email" SortExpression="Email" />
                <asp:BoundField DataField="CompanyName" HeaderText="CompanyName" 
                    SortExpression="CompanyName" />
            </Columns>
        </asp:GridView>
        <asp:ObjectDataSource ID="ObjectDataSource1" runat="server" 
            OldValuesParameterFormatString="original_{0}" SelectMethod="GetUsers" 
            TypeName="FilePark.BusinessLayer.UserManager"></asp:ObjectDataSource>