-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathdcam_framework.py
155 lines (126 loc) · 4.64 KB
/
dcam_framework.py
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
import random
import datetime
class Timestamp:
stamp = None
stamp_type = 'start'
def __init__(self, stamp, stamp_type):
self.stamp = stamp
self.stamp_type = stamp_type
def __sub__(self, other):
if other.stamp_type == 'start' and self.stamp_type == 'end':
return self.stamp - other.stamp
else:
return other.stamp - self.stamp
def __str__(self):
return str(self.stamp) + '|' + self.stamp_type
class Task:
def __init__(self, name: str, full_duration: datetime.timedelta, subject=''):
self.name = name
self.subject = subject
self.timestamps = []
self.running = False
self.full_duration = full_duration
def start(self):
'''for ts in self.timestamps:
print(ts)'''
if not self.running:
self.timestamps.append(Timestamp(datetime.datetime.now(), 'start'))
self.running = True
# print(len(self.timestamps), self.running)
def get_duration(self, end=None):
d = datetime.timedelta()
if not end:
end = datetime.datetime.now()
start = end
for timestamp in self.timestamps:
if timestamp.stamp_type == 'start':
start = timestamp.stamp
elif timestamp.stamp_type == 'end':
d += timestamp.stamp - start
if self.timestamps:
last = self.timestamps[-1]
if last.stamp_type == 'start':
d += end - last.stamp
return d
def end(self):
self.timestamps.clear()
self.running = False
def pause(self):
if len(self.timestamps) > 0 and self.running:
self.timestamps.append(Timestamp(datetime.datetime.now(), 'end'))
self.running = False
def timedelta_to_str(td: datetime.timedelta, mode=''):
if mode == 'by_minutes':
return str(td.total_seconds() / 60) + ' min'
elif mode == 'by_hours':
return str(td.total_seconds() / 3600) + ' h'
elif mode == 'by_seconds':
return str(td.total_seconds()) + ' s'
else:
if td.days:
days = str(td.days) + 'd '
else:
days = ''
hours_num = int(td.total_seconds() // 3600 % 24)
if hours_num:
hours = str(hours_num) + 'h '
else:
hours = ''
minutes_num = int(td.total_seconds() // 60 % 60)
if minutes_num:
minutes = str(minutes_num) + 'min '
else:
minutes = ''
seconds_num = int(td.total_seconds() % 60)
if seconds_num:
seconds = str(seconds_num) + 's '
else:
if td.days or hours_num or minutes_num:
seconds = ''
else:
seconds = '0s'
time_str = days + hours + minutes + seconds
if time_str.endswith(' '):
time_str = time_str[:-1]
return time_str
class Note:
def __init__(self, content: str, time: datetime.datetime):
self.content = content
self.time = time
class Event:
def __init__(self, name, fixed_total_full_duration: datetime.timedelta
, type='未命名事件'
, frequency='permanent'
, color="#%02x%02x%02x" % (180, 180, 180)
, start_time=datetime.datetime.now()
, end_time=datetime.datetime.now() + datetime.timedelta(minutes=20)):
self.name = name
self.type = type
self.color = color
self.start_time = start_time
self.end_time = end_time
self.frequency = frequency
self.tasks = []
self.fixed_total_full_duration = fixed_total_full_duration
def change_color_by_random(self):
self.color = "#%02x%02x%02x" % (random.randint(40, 220), random.randint(40, 220), random.randint(40, 220))
def get_duration(self):
duration = datetime.timedelta()
for task in self.tasks:
duration += task.get_duration()
return duration
def get_total_subject_duration(self, plan_filename: str, end_time=None):
if not end_time:
end_time = self.end_time
subject_names = []
with open(plan_filename, 'rt', encoding='utf-8') as file_input:
subject_names = [line.strip().split('\t')[0] for line in file_input.readlines()]
duration = datetime.timedelta()
for task in self.tasks:
if task.subject in subject_names:
duration += task.get_duration(end=end_time)
return duration
def numerical_grad_1d(f, x, delta=1e-6):
f_l, f_r = f(x + delta), f(x - delta)
grad = (f_l - f_r) / (2 * delta)
return grad