網站首頁 編程語言 正文
為啥要自研
市面主流定時器計劃任務語法: cron ,但是使用起來非常難受,設計的比較非人性話語法,我想一般人都沒幾個記住的,都是靠在線生成工具進行使用的,而且只能持續執行不是有限執行,下面舉幾個cron的案例:
具體想了解的可以自行百度,我試圖記住語法,但是因為太混亂了,時間一長就忘了,沒法只能到網上工具里生成,而且很多有限的場景沒法生成因為cron不支持只執行幾次或者有規律的執行,為了解決以上的問題,我自己研究了一套(free time)定時器計劃任務語法
語法格式
語法: 0,0,7,0,0,0,0,- 長度為8
對應時間: 秒,分,時,天,星期,月,年,執行計劃
執行計劃
數值: 執行幾次
n: 循環執行
^n: 時間乘階 2*2,4*2,8*2....
^數值: 時間乘階幾次 ^2 那么就是2*2,4*2
符號
~: 區間 1~4 那么就會執行1,2,3,4
/: 間隔 2/5 那么從2開始下次之后就從5開始執行
[]: 分段 [1,5,10,12] 分別在這幾個時間點執行
模式
模式就是可以: 月底,月初,每周幾,星期末,年末,節假日等,(可以支持自定義擴張需要對外提供生成器)
執行計劃: m(循環執行) ,m數值(有限執行)
begin: 時間底(天底,周末,月底,年底)
end: 時間初(天初,周初,月初,年初)
point(?): 指定時間點,指定每月5號,每周3,每2天
以上是基礎模式,其他模式需要自定義(節假日,特殊日期等)
注意: 在模式的基礎上還可以配合時間比如: (每天2點1分10秒執行)
語法演示
基本操作
都是以當前時間為基準進行添加時間
當前時間+1分鐘后執行(執行2次)
0,1,0,0,0,0,0,2
(2022-09-24 16:22:59,2022-09-24 16:23:59)
當前時間+5小時后執行(循環執行)
0,0,5,0,0,0,0,n
(2022-09-24 21:23:09,2022-09-25 02:23:09)
當前時間+1天后執行
0,0,0,1,0,0,0,n
(2022-09-25 16:24:07,2022-09-26 16:24:07)
當前時間+1星期(7天)后執行
0,0,0,0,1,0,0,n
(2022-10-01 16:25:19,2022-10-08 16:25:19)
當前時間加1天1小時1分1秒后執行
1,1,1,1,0,0,0,2
(2022-09-25 17:38:57,2022-09-26 18:39:58)
當前時間分鐘遞增執行(循環)
0,1,0,0,0,0,0,^n
當前時間分鐘遞增執行(次數)
0,1,0,0,0,0,0,^2
符號操作
符號操作有~和[]以及/ 可以配合有限和循環n,不能使用遞增
區間執行(循環)
0,2~5,0,0,0,0,0,n(每2分鐘3分鐘…5分鐘各執行一次,然后反復)
間隔執行
0,0,3/0,1,0,0,0,n (3小時后,每天執行一次)
分段執行
0,0,[2,5,8],0,0,0,0,n (當前時間每2,5,8小時執行一次,然后反復)
符號操作還可以和基本操作組合,原理就是相加
0,10,[2,5,8],0,0,0,0,n(當前時間每2,5,8小時加10分鐘執行一次,然后反復)
模式操作
在[年,月,星期,天,小時,分支,秒]底執行
年底執行5次
0,0,0,0,0,0,end,mode5
(2023-12-31 23:59:59 ,2024-12-31 23:59:59)
月底執行,一共執行兩次
0,0,0,0,0,end,0,mode2
(2022-10-31 23:59:59,2022-11-31 23:59:59)
每個星期日底執行(循環)
0,0,0,0,end,0,0,mode
(2022-10-02 23:59:59,2022-10-09 23:59:59)
每天底執行
0,0,0,end,0,0,0,mode
(2022-09-24 23:59:59 , 2022-09-25 23:59:59)
每小時底執行
0,0,end,0,0,0,0,mode
(2022-09-23 15:59:59,2022-09-23 16:59:59)
每分鐘底執行
0,end,0,0,0,0,0,mode
(2022-09-23 14:20:59,2022-09-23 14:21:59)
每秒底執行
end,0,0,0,0,0,0,mode (可能看不出來,所以當做每秒執行就行)
(2022-09-23 14:21:26,2022-09-23 14:22:25)
在[年,月,星期,天,小時,分支,秒]初執行
每年初執行(2次)
0,0,0,0,0,0,begin,mode2
(2023-01-01 00:00:00, 2024-01-01 00:00:00)
沒月初執行
0,0,0,0,0,begin,0,mode2
(2022-10-01 00:00:00, 2022-11-01 00:00:00)
每星期初執行
0,0,0,0,begin,0,0,mode
(2022-09-26 00:00:00,2022-10-03 00:00:00)
每天初執行
0,0,0,begin,0,0,0,mode
(2022-09-25 00:00:00,2022-09-26 00:00:00)
每小時初執行
0,0,begin,0,0,0,0,mode
(2022-09-24 16:00:00,2022-09-24 17:00:00)
每分鐘初執行
0,begin,0,0,0,0,0,mode
(2022-09-24 15:35:00,2022-09-24 15:36:00)
每秒鐘初執行
begin,0,0,0,0,0,0,mode (可能看不出來,所以當做每秒執行就行)
(2022-09-24 15:35:17,2022-09-24 15:35:18)
指定時間執行
我們可以使用模式中的point(?) 來完成,而point除了在星期占位特殊可以指定下個星期幾執行,在其他占位也是可以指定時間
每個星期2晚上11點執行
0,0,point(23),0,point(2),0,0,mode
(2022-09-27 22:00:00,2022-10-04 22:00:00)
每天凌晨2點執行
0,0,point(2),point(1),0,0,0,mode
(2022-09-25 02:00:00,2022-09-26 02:00:00)
模式組合
注意: end ,begin 和point 不能同時出現,但是我們可以和基本模式作進行混合
-59,1,-2,end,0,0,0,mode (每天晚上10點執行)
0,0,8,begin,0,0,0,mode (每天早上8點執行)
0,0,8,point(2),0,0,0,mode (每2天8點執行)
頭文件
#ifndef STUDY_TIMER_RESOLVER_H
#define STUDY_TIMER_RESOLVER_H
#include "time_util.h"
#include "../util/str_util.h"
#include "assertmy.h"
#include <stdio.h>
#include <stdlib.h>
//秒,分鐘,小時,天,星期,月,年,執行計劃 -,-,-,-,-,-,-,- 代表0秒,0分,0小時,0天,星期,0月,0年,不執行
typedef struct timer_resolver {
char *second;//秒 0-59
char *minute;//分鐘 0-59
char *hour; //小時0-23
char *day; //天 1-31
char *week;//星期 0-6
char *month;//月份 1-12
char *year;//年
char *plan;//執行計劃 -代表不執行,n 循環執行,數字代表執行次數 , ^n 階級執行(^1 表示一階執行,^2 表示二階執行,^3 表示三階執行...^n表示n階執行) mode 代表執行模式 mode2 代表模式執行2次....
long timestamp;//時間戳 用于計算下次執行時間
char *help;//協助計算的字段
CharHashMap *mode;//模式
} TimerResolver;
typedef int (*ModeMethod)(char *item,int seat,TimerResolver *timerResolver); //自定義模式方法
TimerResolver *create_timer_resolver(char *time);
void print_timer_resolver(TimerResolver *timerResolver);
long resolver(TimerResolver *timerResolver);
void switchStructure(TimerResolver *timerResolver);
void add_timer_mode(TimerResolver *timerResolver, char *key, ModeMethod method);
void print_format_resolver(TimerResolver *timerResolver, int n);
#endif //STUDY_TIMER_RESOLVER_H
實現文件
#include "timer_resolver.h"
char *get_return_data(char **data1);
//獲取以當前時間后指定年月日時分秒
long time_point_mode(char *item, int seat, TimerResolver *timerResolver) {
//解析point(?)模式,取出?的值
int i = str_find(item, "(");
item = str_substring(item, i + 1, str_length(item) - 2);
if (seat == 0) { //加秒數
return get_next_time_by_timestamp(timerResolver->timestamp, 0, 0, 0, 0, 0, str_to_int(item));
} else if (seat == 1) { //分鐘數
return get_next_time_by_timestamp(timerResolver->timestamp, 0, 0, 0, 0, str_to_int(item), 0);
} else if (seat == 2) { //小時數
return get_next_time_by_timestamp(timerResolver->timestamp, 0, 0, 0, str_to_int(item), 0, 0);
} else if (seat == 3) { //天數
return get_next_time_by_timestamp(timerResolver->timestamp, 0, 0, str_to_int(item), 0, 0, 0);
} else if (seat == 4) { //周n的日期
return get_next_week_of_day(timerResolver->timestamp, str_to_int(item));
} else if (seat == 5) { //月數
return get_next_time_by_timestamp(timerResolver->timestamp, 0, str_to_int(item), 0, 0, 0, 0);
} else if (seat == 6) { //年數
return get_next_time_by_timestamp(timerResolver->timestamp, str_to_int(item), 0, 0, 0, 0, 0);
}
}
// 判斷指定時間,初的時間
long time_begin_mode(char *item, int seat, TimerResolver *timerResolver) {
if (seat == 0) { //秒數
return get_start_time_of_next_second(timerResolver->timestamp);
} else if (seat == 1) { //分鐘數
return get_start_time_of_next_minute(timerResolver->timestamp);
} else if (seat == 2) { //小時數
return get_start_time_of_next_hour(timerResolver->timestamp);
} else if (seat == 3) {// 天數
return get_start_time_of_next_day(timerResolver->timestamp);
} else if (seat == 4) {// 星期數
return get_time_next_week_start(timerResolver->timestamp);
} else if (seat == 5) {// 月數
return get_start_time_of_next_month(timerResolver->timestamp);
} else if (seat == 6) {// 年數
return get_start_time_of_next_year(timerResolver->timestamp);
}
}
// 判斷指定時間,末的時間
long time_end_mode(char *item, int seat, TimerResolver *timerResolver) {
if (seat == 0) { //秒數
return timerResolver->timestamp+59;
} else if (seat == 1) { //分鐘數(如果當前時間是59秒,則返回下一分鐘的59秒)
return get_end_time_of_next_minute(timerResolver->timestamp) ;
} else if (seat == 2) { //小時數
return get_end_time_of_next_hour(timerResolver->timestamp) ;
} else if (seat == 3) { //天數
return get_end_time_of_next_day(timerResolver->timestamp) ;
} else if (seat == 4) { //星期數(周末開始時間)
return get_end_time_of_next_week(timerResolver->timestamp);
} else if (seat == 5) { //月數
return get_end_time_of_next_month(timerResolver->timestamp) ;
} else if (seat == 6) { //年數
return get_end_time_of_next_year(timerResolver->timestamp) ;
}
}
// 判斷是否有此模式
BOOL mode_exist(char *item, TimerResolver *timerResolver) {
if(!str_contains(timerResolver->plan,"mode")){
return FALSE;
}
CharHashMapIterator *pIterator = createCharHashMapIterator(timerResolver->mode);
while (hasNextCharHashMapIterator(pIterator)) {
CharKvLinkedNode *pNode = nextCharHashMapIterator(pIterator);
if (str_start_with(item,pNode->key )) {//如果匹配到模式,那么就轉換為統一結構化格式
return TRUE;
}
}
return FALSE;
}
//模式解析
long mode_timer(char *item, int seat, TimerResolver *timerResolver) {
if (str_contains(timerResolver->plan, "mode")) {
CharHashMapIterator *pIterator = createCharHashMapIterator(timerResolver->mode);
while (hasNextCharHashMapIterator(pIterator)) {
CharKvLinkedNode *pNode = nextCharHashMapIterator(pIterator);
if (str_start_with(item,pNode->key)) {//如果匹配到模式
ModeMethod pVoid = (ModeMethod) pNode->value;
return pVoid(item, seat, timerResolver);//執行模式方法
}
}
}
return 0;// 沒有匹配到模式
}
//添加模式方法(如果執行計劃為mode,則支持)
void add_timer_mode(TimerResolver *timerResolver, char *key, ModeMethod method) {
if (str_contains(timerResolver->plan, "mode")) {
putCharHashMap(timerResolver->mode, key, method);//添加模式方法
}
}
void inside_add_timer_mode(TimerResolver *timerResolver) {
if (str_contains(timerResolver->plan, "mode")) {
add_timer_mode(timerResolver, "begin", time_begin_mode);
add_timer_mode(timerResolver, "end", time_end_mode);
add_timer_mode(timerResolver, "point", time_point_mode);
}
}
//獲取下一次執行時間,返回時間戳
long get_next_time(TimerResolver *timerResolver) {
if (!timerResolver->plan) {
return 0;
}
if (str_contains(timerResolver->plan, "mode")) {
long mode_timer1 = mode_timer(get_return_data(&timerResolver->second), 0, timerResolver);
timerResolver->timestamp+=get_time_difference_second(timerResolver->timestamp, mode_timer1);
long mode_timer2 = mode_timer(get_return_data(&timerResolver->minute), 1, timerResolver);
timerResolver->timestamp+=get_time_difference_second(timerResolver->timestamp,mode_timer2 );
long mode_timer3= mode_timer(get_return_data(&timerResolver->hour), 2, timerResolver);
timerResolver->timestamp+=get_time_difference_second(timerResolver->timestamp,mode_timer3 );
long mode_timer4 = mode_timer(get_return_data(&timerResolver->day), 3, timerResolver);
timerResolver->timestamp+=get_time_difference_second(timerResolver->timestamp, mode_timer4);
long mode_timer5 = mode_timer(get_return_data(&timerResolver->week), 4, timerResolver);
timerResolver->timestamp+=get_time_difference_second(timerResolver->timestamp, mode_timer5);
long mode_timer6 = mode_timer(get_return_data(&timerResolver->month), 5, timerResolver);
timerResolver->timestamp+=get_time_difference_second(timerResolver->timestamp, mode_timer6);
long mode_timer7 = mode_timer(get_return_data(&timerResolver->year), 6, timerResolver);
timerResolver->timestamp+=get_time_difference_second(timerResolver->timestamp, mode_timer7);
}
long current = timerResolver->timestamp;
//獲取當前時間
int second = str_to_int(get_return_data(&timerResolver->second));
int minute = str_to_int(get_return_data(&timerResolver->minute));
int hour = str_to_int(get_return_data(&timerResolver->hour));
int day = str_to_int(get_return_data(&timerResolver->day));
int week = str_to_int(get_return_data(&timerResolver->week));
int month = str_to_int(get_return_data(&timerResolver->month));
int year = str_to_int(get_return_data(&timerResolver->year));
long newTime = add_time_one(current,
second,
minute,
hour,
day,
month,
year,
week
);
timerResolver->timestamp = newTime;
if(str_contains(timerResolver->plan,"mode")){
return newTime;
}else{
return current;
}
}
//解析字符串-,-,-,-,-,-,-,-并創建TimerResolver
TimerResolver *create_timer_resolver(char *time) {
if (time == NULL && strlen(time) == 0) {
return NULL;
}
//去空
time = str_trim(time);
//排除[]內的,號
int start = 0;
while ((start = str_find_n(time, "[", start, str_length(time))) != -1) {
int end = str_find_n(time, "]", start, str_length(time));
time = str_replace_all_n(time, ",", "@", start, end);
start++;
}
TimerResolver *timerResolver = (TimerResolver *) malloc(sizeof(TimerResolver));
if (timerResolver == NULL) {
return NULL;
}
CharList *pCharlist = str_split(time, ",");
int str_len = pCharlist->len;
if (str_len != 8) {
char message[100];
sprintf(message, "create_timer_resolver語法錯誤: %s ", time);
assertError(message);
}
timerResolver->second = pCharlist->str[0];
timerResolver->minute = pCharlist->str[1];
timerResolver->hour = pCharlist->str[2];
timerResolver->day = pCharlist->str[3];
timerResolver->week = pCharlist->str[4];
timerResolver->month = pCharlist->str[5];
timerResolver->year = pCharlist->str[6];
timerResolver->timestamp = get_current_timestamp();//獲取當前時間戳
//執行計劃 -代表不執行,n 循環執行,數字代表執行次數 , ^n 階級執行(^1 表示一階執行,^2 表示二階執行,^3 表示三階執行...^n表示n階執行)
timerResolver->plan = str_compare(pCharlist->str[7], "-") ? "0" : pCharlist->str[7];
timerResolver->help = "{}";
timerResolver->mode = createCharHashMap(10);
//添加模式方法
inside_add_timer_mode(timerResolver);
//轉換為結構化格式
switchStructure(timerResolver);
//計算本次執行時間
if(!str_contains(timerResolver->plan,"mode")){
get_next_time(timerResolver);
}
return timerResolver;
}
//打印TimerResolver,格式為-,-,-,-,-,-,-,-
void print_timer_resolver(TimerResolver *timerResolver) {
printf("%s,%s,%s,%s,%s,%s,%s,%s\n", timerResolver->second, timerResolver->minute, timerResolver->hour,
timerResolver->day, timerResolver->week, timerResolver->month, timerResolver->year,
timerResolver->plan);
}
//執行n次定時器并且打印效果
void print_format_resolver(TimerResolver *timerResolver, int n) {
for (int i = 0; i < n; ++i){
long i1 = resolver(timerResolver);
char *string = format_time(i1, "%Y-%m-%d %H:%M:%S");
printf("%ld---%s\n",i1,string);
}
}
//解析定時器語法,并且生成下次執行時間,如果返回0,則此語法已經執行結束了,可以刪除對應的定時器了
long resolver(TimerResolver *timerResolver) {
//判斷是否可執行
if (str_equals(timerResolver->plan,"0") ) {//不執行
return 0;
}
if (str_compare(timerResolver->plan, "n")) {//循環執行
return get_next_time(timerResolver);
}
//階級執行
if (str_start_with(timerResolver->plan, "^")) {
CharHashMap *pMapSecond = str_to_json_map(timerResolver->second);
putCharHashMap(pMapSecond, "return",
int_to_str(str_to_int(get_return_data(&timerResolver->second)) * 2));
timerResolver->second = map_to_json_str(pMapSecond);
CharHashMap *pMapMinute = str_to_json_map(timerResolver->minute);
putCharHashMap(pMapMinute, "return",
int_to_str(str_to_int(get_return_data(&timerResolver->minute)) * 2));
timerResolver->minute = map_to_json_str(pMapMinute);
CharHashMap *pMapHour = str_to_json_map(timerResolver->hour);
putCharHashMap(pMapHour, "return",
int_to_str(str_to_int(get_return_data(&timerResolver->hour)) * 2));
timerResolver->hour = map_to_json_str(pMapHour);
CharHashMap *pMapDay = str_to_json_map(timerResolver->day);
putCharHashMap(pMapDay, "return",
int_to_str(str_to_int(get_return_data(&timerResolver->day)) * 2));
timerResolver->hour = map_to_json_str(pMapDay);
CharHashMap *pMapWeek = str_to_json_map(timerResolver->week);
putCharHashMap(pMapWeek, "return",
int_to_str(str_to_int(get_return_data(&timerResolver->week)) * 2));
timerResolver->week = map_to_json_str(pMapWeek);
CharHashMap *pMapMonth = str_to_json_map(timerResolver->month);
putCharHashMap(pMapMonth, "return",
int_to_str(str_to_int(get_return_data(&timerResolver->month)) * 2));
timerResolver->month = map_to_json_str(pMapMonth);
CharHashMap *pMapYear = str_to_json_map(timerResolver->year);
putCharHashMap(pMapYear, "return",
int_to_str(str_to_int(get_return_data(&timerResolver->year)) * 2));
timerResolver->year = map_to_json_str(pMapYear);
char *string = str_substring(timerResolver->plan, 1, str_length(timerResolver->plan));
if (str_compare(string, "n")) { //如果是n那么就是循環執行
return get_next_time(timerResolver);
}
if (str_is_number(string)) {//如果是數字,那么就是有限階級執行
if (str_compare(string, "0")) {
return 0;
}
char *one = str_calculate_one(string, "--");
timerResolver->plan = str_concat(2, "^", one);
return get_next_time(timerResolver);
}
}
//模式執行
if (str_start_with(timerResolver->plan, "mode")) {
timerResolver->timestamp= get_start_time_of_day(timerResolver->timestamp );// 初始化為當天的開始時間 ,然后在后面的計算中,加上指定的時間
if (str_length(timerResolver->plan) == 4) { //循環執行
return get_next_time(timerResolver);
} else {
char *string = str_substring(timerResolver->plan, 4, str_length(timerResolver->plan));
if (str_is_number(string)) {//如果是數字,那么就是有限階級執行
if (str_compare(string, "0")) {
return 0;
}
char *one = str_calculate_one(string, "--");
timerResolver->plan = str_concat(2, "mode", one);
return get_next_time(timerResolver);
} else {
assertError(formatStr("mode解析錯誤非法字符(必須是mode+數字):%s\n", timerResolver->plan));
}
}
}
//有限執行
if (str_is_number(timerResolver->plan)) {
int plan = str_to_int(timerResolver->plan);
if (plan > 0) {
timerResolver->plan = int_to_str(plan - 1);
return get_next_time(timerResolver);
}
}
}
//分段[]解析
char *section_analysis(char *item, TimerResolver *timerResolver) {
//在幫助里存儲當前的次數
CharHashMap *pMap = str_to_json_map(timerResolver->help);
if (!containsKeyCharHashMap(pMap, "basicsPlan")) {
putCharHashMap(pMap, "basicsPlan", timerResolver->plan);
timerResolver->help = map_to_json_str(pMap);
}
//將[]里面的@轉換為,號
item = str_replace_all_n(item, "@", ",", 0, str_length(item));
CharList *pCharlist = str_to_json_array(item);
//驗證是否都是數字
for (int i = 0; i < pCharlist->len; ++i) {
if (!str_is_number(pCharlist->str[i])) {
assertError(formatStr("[]解析錯誤非法字符(必須是數字):%s\n", pCharlist->str[i]));
}
}
char *string = str_concat(11, "{", "type:[]", ",", "data:", item, ",", "index:0", ",", "return:",
pCharlist->str[0], "}");
//添加執行的次數
CharHashMap *pMap1 = str_to_json_map(timerResolver->help);
char *basicsPlan = getCharHashMap(pMap1, "basicsPlan");
if(str_equals(basicsPlan,"n")||str_start_with(basicsPlan,"^")){
timerResolver->plan = timerResolver->plan;
}else{
if (str_equals(timerResolver->plan, basicsPlan)) {
timerResolver->plan = int_to_str(pCharlist->len * str_to_int(basicsPlan));
} else {
timerResolver->plan = int_to_str(
str_to_int(timerResolver->plan) + (pCharlist->len * str_to_int(basicsPlan)));
}
}
return string;
}
//區間解析 符號為~ ,位置1表示秒,2表示分支,3表示小時,4表示天,5表示星期,6表示月,7表示年
char *range_analysis(char *item, TimerResolver *timerResolver) {
//在幫助里存儲當前的次數
CharHashMap *pMap = str_to_json_map(timerResolver->help);
if (!containsKeyCharHashMap(pMap, "basicsPlan")) {
putCharHashMap(pMap, "basicsPlan", timerResolver->plan);
timerResolver->help = map_to_json_str(pMap);
}
CharList *pCharlist = str_split(item, "~");
//驗證是否都是數字
for (int i = 0; i < pCharlist->len; ++i) {
if (!str_is_number(pCharlist->str[i])) {
assertError(formatStr("~解析錯誤非法字符(必須是數字):%s\n", pCharlist->str[i]));
}
}
CharList *range = get_range(pCharlist->str[0], pCharlist->str[1]);
char *data = array_to_json_str(range);
char *string = str_concat(11, "{", "type:~", ",", "data:", data, ",", "index:0", ",", "return:", range->str[0],
"}");
//添加執行的次數
CharHashMap *pMap1 = str_to_json_map(timerResolver->help);
char *basicsPlan = getCharHashMap(pMap1, "basicsPlan");
if(str_equals(basicsPlan,"n")||str_start_with(basicsPlan,"^")){
timerResolver->plan = timerResolver->plan;
}else{
if (str_equals(timerResolver->plan, basicsPlan)) {
timerResolver->plan = int_to_str(range->len * str_to_int(basicsPlan));
} else {
timerResolver->plan = int_to_str(str_to_int(timerResolver->plan) + (range->len * str_to_int(basicsPlan)));
}
}
return string;
}
//間隔/ 解析 (5/2)表示從5開始,每隔2個數 執行一次
char *interval_analysis(char *item, TimerResolver *timerResolver) {
//在幫助里存儲當前的次數
CharHashMap *pMap = str_to_json_map(timerResolver->help);
if (!containsKeyCharHashMap(pMap, "basicsPlan")) {
putCharHashMap(pMap, "basicsPlan", timerResolver->plan);
timerResolver->help = map_to_json_str(pMap);
}
CharList *pCharlist = str_split(item, "/");
//驗證是否都是數字
for (int i = 0; i < pCharlist->len; ++i) {
if (!str_is_number(pCharlist->str[i])) {
assertError(formatStr("/解析錯誤非法字符(必須是數字):%s\n", pCharlist->str[i]));
}
}
char *data = str_concat(5, "[", pCharlist->str[0], ",", pCharlist->str[1], "]");
char *string = str_concat(11, "{", "type:/", ",", "data:", data, ",", "index:0", ",", "return:", pCharlist->str[0],
"}");
//添加執行的次數
CharHashMap *pMap1 = str_to_json_map(timerResolver->help);
char *basicsPlan = getCharHashMap(pMap1, "basicsPlan");
if(str_equals(basicsPlan,"n")||str_start_with(basicsPlan,"^")){
timerResolver->plan = timerResolver->plan;
}else{
if (str_equals(timerResolver->plan, basicsPlan)) {
timerResolver->plan = int_to_str(str_to_int(basicsPlan) + 1);
}
}
return string;
}
char *mode_analysis(char *item, TimerResolver *timerResolver) {
CharHashMapIterator *pIterator = createCharHashMapIterator(timerResolver->mode);
while (hasNextCharHashMapIterator(pIterator)) {
CharKvLinkedNode *pNode = nextCharHashMapIterator(pIterator);
if (str_start_with(item,pNode->key)) {//如果匹配到模式,那么就轉換為統一結構化格式
char *string = str_concat(6, "{", "type:mode", ",", "return:", item, "}");
return string;
}
}
assertError(formatStr("mode模式解析錯誤沒有找到對應的模式-請檢查模式是否自定義-并且添加到模式集中:%s\n", item));
}
//普通解析
char *normal_analysis(char *item) {
if (str_is_number(item)) {
char *string = str_concat(6, "{", "type:number", ",", "return:", item, "}");
return string;
}
assertError(formatStr("解析錯誤,無法解析的表達式:%s\n", item));
}
//獲取結構化數據的返回數據
char *get_return_data(char **data1) {
char *data = *data1;
//判斷是否是字典格式
if (str_is_map(data)) {
//解析字典
CharHashMap *pMap = str_to_json_map(data);
//獲取類型
char *type = getCharHashMap(pMap, "type");
//如果類型是[]
if (str_compare(type,
"[]")) { //如果是[]類型 那么就是分段 例如 [1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19,20,21,22,23,24]
//獲取data
char *data = getCharHashMap(pMap, "data");
//獲取index
char *index = getCharHashMap(pMap, "index");
//獲取返回數據
char *returnData = getCharHashMap(pMap, "return");
//獲取數組
//將[]里面的@轉換為,號
CharList *pCharlist = str_to_json_array(data);
//獲取下一個值
int nextIndex = str_to_int(index) + 1;
//判斷是否超出數組長度,如果超出長度,從頭開始
if (nextIndex >= pCharlist->len) {
//超出長度,返回空
nextIndex = 0;
}
//獲取下一個值
char *nextValue = pCharlist->str[nextIndex];
//設置返回數據
putCharHashMap(pMap, "return", nextValue);
//設置index
putCharHashMap(pMap, "index", int_to_str(nextIndex));
//修改原數據
*data1 = map_to_json_str(pMap);
//返回數據
return returnData;
} else if (str_compare(type, "~")) { //如果類型是~ 那么就是區間 1~5 表示1,2,3,4,5
//如果類型是~
//獲取data
char *data = getCharHashMap(pMap, "data");
//獲取index
char *index = getCharHashMap(pMap, "index");
//獲取返回數據
char *returnData = getCharHashMap(pMap, "return");
//獲取數組
CharList *pCharlist = str_to_json_array(data);
//獲取下一個值
int nextIndex = str_to_int(index) + 1;
//判斷是否超出數組長度,如果超出長度,從頭開始
if (nextIndex >= pCharlist->len) {
nextIndex = 0;
}
//獲取下一個值
char *nextValue = pCharlist->str[nextIndex];
//設置返回數據
putCharHashMap(pMap, "return", nextValue);
//設置index
putCharHashMap(pMap, "index", int_to_str(nextIndex));
//修改原數據
*data1 = map_to_json_str(pMap);
//返回數據
return returnData;
} else if (str_compare(type, "/")) { // 如果類型是/ (5/2)表示從5開始,每隔2個數 執行一次
//如果類型是/
//獲取data
char *data = getCharHashMap(pMap, "data");
//獲取index
char *index = getCharHashMap(pMap, "index");
//獲取返回數據
char *returnData = getCharHashMap(pMap, "return");
int nextIndex = str_to_int(index) + 1;
if (nextIndex == 1) {
//獲取數組
CharList *pCharlist = str_to_json_array(data);
//判斷index是否是1,如果是1,取第二個值,并且轉換為普通結構
char *string = str_concat(6, "{", "type:number", ",", "return:", pCharlist->str[nextIndex], "}");
*data1 = string;
}
return returnData;
} else if (str_compare(type, "number")) {
//如果類型是number,那么獲取return
char *returnData = getCharHashMap(pMap, "return");
return returnData;
}else if (str_compare(type, "mode")) {
//如果類型是mode,那么獲取return
char *returnData = getCharHashMap(pMap, "return");
return returnData;
}
}
assertError(formatStr("解析錯誤不是結構化數據: %s\n", data));
}
//定時器語法轉換為結構化格式
void switchStructure(TimerResolver *timerResolver) {
//秒
if (str_contains(timerResolver->second, "[")) {
timerResolver->second = section_analysis(timerResolver->second, timerResolver);
} else if (str_contains(timerResolver->second, "~")) {
timerResolver->second = range_analysis(timerResolver->second, timerResolver);
} else if (str_contains(timerResolver->second, "/")) {
timerResolver->second = interval_analysis(timerResolver->second, timerResolver);
} else if (mode_exist(timerResolver->second, timerResolver)) {
timerResolver->second = mode_analysis(timerResolver->second, timerResolver);
} else {
timerResolver->second = normal_analysis(timerResolver->second);
}
//分
if (str_contains(timerResolver->minute, "[")) {
timerResolver->minute = section_analysis(timerResolver->minute, timerResolver);
} else if (str_contains(timerResolver->minute, "~")) {
timerResolver->minute = range_analysis(timerResolver->minute, timerResolver);
} else if (str_contains(timerResolver->minute, "/")) {
timerResolver->minute = interval_analysis(timerResolver->minute, timerResolver);
} else if (mode_exist(timerResolver->minute, timerResolver)) {
timerResolver->minute = mode_analysis(timerResolver->minute, timerResolver);
} else {
timerResolver->minute = normal_analysis(timerResolver->minute);
}
//時
if (str_contains(timerResolver->hour, "[")) {
timerResolver->hour = section_analysis(timerResolver->hour, timerResolver);
} else if (str_contains(timerResolver->hour, "~")) {
timerResolver->hour = range_analysis(timerResolver->hour, timerResolver);
} else if (str_contains(timerResolver->hour, "/")) {
timerResolver->hour = interval_analysis(timerResolver->hour, timerResolver);
} else if (mode_exist(timerResolver->hour, timerResolver)) {
timerResolver->hour = mode_analysis(timerResolver->hour, timerResolver);
} else {
timerResolver->hour = normal_analysis(timerResolver->hour);
}
//日
if (str_contains(timerResolver->day, "[")) {
timerResolver->day = section_analysis(timerResolver->day, timerResolver);
} else if (str_contains(timerResolver->day, "~")) {
timerResolver->day = range_analysis(timerResolver->day, timerResolver);
} else if (str_contains(timerResolver->day, "/")) {
timerResolver->day = interval_analysis(timerResolver->day, timerResolver);
} else if (mode_exist(timerResolver->day, timerResolver)) {
timerResolver->day = mode_analysis(timerResolver->day, timerResolver);
} else {
timerResolver->day = normal_analysis(timerResolver->day);
}
//周
if (str_contains(timerResolver->week, "[")) {
timerResolver->week = section_analysis(timerResolver->week, timerResolver);
} else if (str_contains(timerResolver->week, "~")) {
timerResolver->week = range_analysis(timerResolver->week, timerResolver);
} else if (str_contains(timerResolver->week, "/")) {
timerResolver->week = interval_analysis(timerResolver->week, timerResolver);
} else if (mode_exist(timerResolver->week, timerResolver)) {
timerResolver->week = mode_analysis(timerResolver->week, timerResolver);
} else {
timerResolver->week = normal_analysis(timerResolver->week);
}
//月
if (str_contains(timerResolver->month, "[")) {
timerResolver->month = section_analysis(timerResolver->month, timerResolver);
} else if (str_contains(timerResolver->month, "~")) {
timerResolver->month = range_analysis(timerResolver->month, timerResolver);
} else if (str_contains(timerResolver->month, "/")) {
timerResolver->month = interval_analysis(timerResolver->month, timerResolver);
} else if (mode_exist(timerResolver->month, timerResolver)) {
timerResolver->month = mode_analysis(timerResolver->month, timerResolver);
} else {
timerResolver->month = normal_analysis(timerResolver->month);
}
//年
if (str_contains(timerResolver->year, "[")) {
timerResolver->year = section_analysis(timerResolver->year, timerResolver);
} else if (str_contains(timerResolver->year, "~")) {
timerResolver->year = range_analysis(timerResolver->year, timerResolver);
} else if (str_contains(timerResolver->year, "/")) {
timerResolver->year = interval_analysis(timerResolver->year, timerResolver);
} else if (mode_exist(timerResolver->year, timerResolver)) {
timerResolver->year = mode_analysis(timerResolver->year, timerResolver);
} else {
timerResolver->year = normal_analysis(timerResolver->year);
}
}
//釋放TimerResolver
void free_timer_resolver(TimerResolver *timerResolver) {
free(timerResolver);
}
原文鏈接:https://blog.csdn.net/weixin_45203607/article/details/127042202
相關推薦
- 2022-03-24 C語言指針的圖文詳解_C 語言
- 2023-09-12 Spring AOP 登錄日志
- 2023-04-08 Swift?HTTP加載請求Loading?Requests教程_Swift
- 2022-07-13 Docker 數據管理
- 2021-12-10 linux防火墻配置(基于yum倉的配置)詳細步驟_Linux
- 2022-07-15 教你docker方式部署nacos_docker
- 2022-06-09 詳解Python中*args和**kwargs的使用_python
- 2022-06-10 C語言?模擬實現strcpy與strcat函數詳解_C 語言
- 最近更新
-
- window11 系統安裝 yarn
- 超詳細win安裝深度學習環境2025年最新版(
- Linux 中運行的top命令 怎么退出?
- MySQL 中decimal 的用法? 存儲小
- get 、set 、toString 方法的使
- @Resource和 @Autowired注解
- Java基礎操作-- 運算符,流程控制 Flo
- 1. Int 和Integer 的區別,Jav
- spring @retryable不生效的一種
- Spring Security之認證信息的處理
- Spring Security之認證過濾器
- Spring Security概述快速入門
- Spring Security之配置體系
- 【SpringBoot】SpringCache
- Spring Security之基于方法配置權
- redisson分布式鎖中waittime的設
- maven:解決release錯誤:Artif
- restTemplate使用總結
- Spring Security之安全異常處理
- MybatisPlus優雅實現加密?
- Spring ioc容器與Bean的生命周期。
- 【探索SpringCloud】服務發現-Nac
- Spring Security之基于HttpR
- Redis 底層數據結構-簡單動態字符串(SD
- arthas操作spring被代理目標對象命令
- Spring中的單例模式應用詳解
- 聊聊消息隊列,發送消息的4種方式
- bootspring第三方資源配置管理
- GIT同步修改后的遠程分支