您好,我有一个表示时间表的结构对象数组。我需要对它们进行排序,以使排序后的第一个元素最接近当前日期。
结构如下:
struct ScheduleItem {
int index;
int hh;
int mm;
int dow;
long reg_timestamp;
};
index
=>任意索引号
hh
=>小时(24)
mm
=>分钟
dow
=>星期几(从星期日开始= 0)
reg_timestamp
=>创建时间表的时代时间
以下是样本时间表,它们存储在名为user_schedules
的时间表数组中。
index:HH:MM:DOW:EPOCH
1:20:30:0:1550951769
2:03:15:0:1550951769
2:20:30:1:1550951769
3:03:15:1:1550951769
3:20:30:2:1550951769
4:03:15:2:1550951769
4:20:30:3:1550951769
5:03:15:3:1550951769
6:03:15:4:1550951769
假设今天是2:00 am
Saturday
(dow = 6)
如何使用qsort对其进行排序
数组按顺序排序,第一个元素是当前日期的closest past
。我只知道升序或降序排序,所以无法得到想要的东西。
这是我尝试过的:
qsort((void *) &applicable_schedules, counter, sizeof(struct ScheduleItem), (compfn)nearestPast );
candidate = applicable_schedules[0];
/**
* Compare to sort nearest past schedule
*/
int nearestPast(struct ScheduleItem *elem1, struct ScheduleItem *elem2)
{
if ( elem1->reg_timestamp == elem2->reg_timestamp)
{
return abs(elem1->dow - elem2->dow);
}
else
{
return elem1->reg_timestamp - elem2->reg_timestamp;
}
}
我得到了20:30:0:1550951769
,Sunday
(课程不正确)
我不是c专家,因此在这种情况下对理解排序有疑问。
此代码适用于arduino
更新
为进一步澄清,最接近的过去应该是星期几以及HH:MM
答案 0 :(得分:1)
如果reg_timestamp
仅是从纪元以来的秒数,并且您想按降序对条目进行排序,那么您要做的就是:
int compare_sched_item_time (const void *a, const void *b)
{
/* cast pointers to adjacent elements to struct ScheduleItem* */
struct ScheduleItem *x = a, *y = b;
/* (x->time < y->time) - (x->time > y->time) - descending sort
* comparison avoids potential overflow
*/
return (x->reg_timestamp < y->reg_timestamp) -
(x->reg_timestamp > y->reg_timestamp);
}
注意:条件表达式的不同避免了潜在的溢出。您可以将其与任何数字类型一起使用。形式为:
/* (a > b) - (a < b) - ascending sort */
和
/* (a < b) - (a > b) - descending sort */
只需仔细考虑案例。为了提升(a > b)
为真(例如1
)和(a < b)
为假(例如0
)的情况,您的条件为1 - 0 = 1
,因此b
进行排序在a
之前。如果它们相等,则结果为0
(无需交换)。如果(a > b)
为假,(a < b)
为真,则结果为-1
,因此a
在b
之前排序-就像strcmp
的结果一样等等。
编辑-如果reg_timestamp
值相等,则进行比较
如果您希望对多个条件进行排序,只需按照重要性递减的顺序进行测试,例如
int compare_sched_item_time (const void *a, const void *b)
{
/* cast pointers to adjacent elements to struct ScheduleItem* */
struct ScheduleItem *x = a, *y = b;
/* (x->time < y->time) - (x->time > y->time) - descending sort
* comparison avoids potential overflow
*/
if (x->reg_timestamp != y->reg_timestamp)
return (x->reg_timestamp < y->reg_timestamp) -
(x->reg_timestamp > y->reg_timestamp);
/* compare dow next */
else if (x->dow != y->dow)
return (x->dow < y->dow) - (x->dow > y->dow);
/* compare hh next */
else if (x->hh != y->hh)
return (x->hh < y->hh) - (x->hh > y->hh);
/* finally compare mm */
else
return (x->mm < y->mm) - (x->mm > y->mm);
}
这是qsort
的好处。您可以按照自己希望的任何方式对任何元素进行排序,只需返回-1, 0, 1
即可达到所需条件。