utilskit 0.2.0__tar.gz → 0.2.1__tar.gz
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- {utilskit-0.2.0 → utilskit-0.2.1}/PKG-INFO +8 -6
- {utilskit-0.2.0 → utilskit-0.2.1}/README.md +7 -5
- {utilskit-0.2.0 → utilskit-0.2.1}/setup.py +1 -1
- {utilskit-0.2.0 → utilskit-0.2.1}/test/test.py +38 -1
- utilskit-0.2.1/utilskit/repeatutils/repeatutils.py +502 -0
- {utilskit-0.2.0 → utilskit-0.2.1}/utilskit/utils/utils.py +1 -0
- {utilskit-0.2.0 → utilskit-0.2.1}/utilskit.egg-info/PKG-INFO +8 -6
- utilskit-0.2.0/utilskit/repeatutils/repeatutils.py +0 -267
- {utilskit-0.2.0 → utilskit-0.2.1}/MANIFEST.in +0 -0
- {utilskit-0.2.0 → utilskit-0.2.1}/setup.cfg +0 -0
- {utilskit-0.2.0 → utilskit-0.2.1}/utilskit/__init__.py +0 -0
- {utilskit-0.2.0 → utilskit-0.2.1}/utilskit/classificationutils/__init__.py +0 -0
- {utilskit-0.2.0 → utilskit-0.2.1}/utilskit/classificationutils/classificationutils.py +0 -0
- {utilskit-0.2.0 → utilskit-0.2.1}/utilskit/dataframeutils/__init__.py +0 -0
- {utilskit-0.2.0 → utilskit-0.2.1}/utilskit/dataframeutils/dataframeutils.py +0 -0
- {utilskit-0.2.0 → utilskit-0.2.1}/utilskit/dbutils/__init__.py +0 -0
- {utilskit-0.2.0 → utilskit-0.2.1}/utilskit/dbutils/dbutils.py +0 -0
- {utilskit-0.2.0 → utilskit-0.2.1}/utilskit/logutils/__init__.py +0 -0
- {utilskit-0.2.0 → utilskit-0.2.1}/utilskit/logutils/logutils.py +0 -0
- {utilskit-0.2.0 → utilskit-0.2.1}/utilskit/plotutils/__init__.py +0 -0
- {utilskit-0.2.0 → utilskit-0.2.1}/utilskit/plotutils/plotutils.py +0 -0
- {utilskit-0.2.0 → utilskit-0.2.1}/utilskit/repeatutils/__init__.py +0 -0
- {utilskit-0.2.0 → utilskit-0.2.1}/utilskit/timeutils/__init__.py +0 -0
- {utilskit-0.2.0 → utilskit-0.2.1}/utilskit/timeutils/timeutils.py +0 -0
- {utilskit-0.2.0 → utilskit-0.2.1}/utilskit/utils/__init__.py +0 -0
- {utilskit-0.2.0 → utilskit-0.2.1}/utilskit.egg-info/SOURCES.txt +0 -0
- {utilskit-0.2.0 → utilskit-0.2.1}/utilskit.egg-info/dependency_links.txt +0 -0
- {utilskit-0.2.0 → utilskit-0.2.1}/utilskit.egg-info/requires.txt +0 -0
- {utilskit-0.2.0 → utilskit-0.2.1}/utilskit.egg-info/top_level.txt +0 -0
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
Metadata-Version: 2.4
|
|
2
2
|
Name: utilskit
|
|
3
|
-
Version: 0.2.
|
|
3
|
+
Version: 0.2.1
|
|
4
4
|
Summary: description
|
|
5
5
|
Author: Kimyh
|
|
6
6
|
Author-email: kim_yh663927@naver.com
|
|
@@ -25,12 +25,14 @@ Dynamic: requires-dist
|
|
|
25
25
|
Dynamic: requires-python
|
|
26
26
|
Dynamic: summary
|
|
27
27
|
|
|
28
|
-
0.2.
|
|
28
|
+
# 0.2.1
|
|
29
|
+
- repeatutila 에 get_section 함수 추가
|
|
30
|
+
# 0.2.0
|
|
29
31
|
- 정식 최초 배포버전
|
|
30
32
|
- 각 함수의 사용성 강화 및 비활성 함수 지정
|
|
31
|
-
0.1.2
|
|
33
|
+
# 0.1.2
|
|
32
34
|
- repeatutils 의 get_repeat_section 에서 하나의 값이 여러 구간에서 반복될때 마지막 구간만 나오는 부분 수정
|
|
33
35
|
- repeatutils 의 get_repeat_section 및 get_stan_repeat_section 에서 추출되는 구간의 마지막 값이 +1 이 되는 부분 수정
|
|
34
|
-
0.1.1
|
|
35
|
-
repeatutils.py 추가
|
|
36
|
-
utils.py 에서 repeat 관련 함수 제거
|
|
36
|
+
# 0.1.1
|
|
37
|
+
- repeatutils.py 추가
|
|
38
|
+
- utils.py 에서 repeat 관련 함수 제거
|
|
@@ -1,9 +1,11 @@
|
|
|
1
|
-
0.2.
|
|
1
|
+
# 0.2.1
|
|
2
|
+
- repeatutila 에 get_section 함수 추가
|
|
3
|
+
# 0.2.0
|
|
2
4
|
- 정식 최초 배포버전
|
|
3
5
|
- 각 함수의 사용성 강화 및 비활성 함수 지정
|
|
4
|
-
0.1.2
|
|
6
|
+
# 0.1.2
|
|
5
7
|
- repeatutils 의 get_repeat_section 에서 하나의 값이 여러 구간에서 반복될때 마지막 구간만 나오는 부분 수정
|
|
6
8
|
- repeatutils 의 get_repeat_section 및 get_stan_repeat_section 에서 추출되는 구간의 마지막 값이 +1 이 되는 부분 수정
|
|
7
|
-
0.1.1
|
|
8
|
-
repeatutils.py 추가
|
|
9
|
-
utils.py 에서 repeat 관련 함수 제거
|
|
9
|
+
# 0.1.1
|
|
10
|
+
- repeatutils.py 추가
|
|
11
|
+
- utils.py 에서 repeat 관련 함수 제거
|
|
@@ -2,7 +2,7 @@ from setuptools import setup, find_packages
|
|
|
2
2
|
|
|
3
3
|
setup(
|
|
4
4
|
name="utilskit", # 패키지 이름 (pip install 시 사용될 이름)
|
|
5
|
-
version="0.2.
|
|
5
|
+
version="0.2.1", # 버전
|
|
6
6
|
packages=find_packages(), # textbasic 폴더 내 모든 패키지 포함
|
|
7
7
|
include_package_data=True, # 이 설정을 통해 패키지 내 데이터 파일을 포함시킬 수 있음
|
|
8
8
|
package_data={
|
|
@@ -317,5 +317,42 @@ def main13():
|
|
|
317
317
|
print(error_info)
|
|
318
318
|
|
|
319
319
|
|
|
320
|
+
def main14():
|
|
321
|
+
import numpy as np
|
|
322
|
+
from utilskit import repeatutils as rpu
|
|
323
|
+
data = np.array(
|
|
324
|
+
[
|
|
325
|
+
1, 1, 1, 1, 1, # 0 ~ 4
|
|
326
|
+
2, 2, 2, 2, # 5 ~ 8
|
|
327
|
+
3, 3, # 9 ~ 10
|
|
328
|
+
4, 4, 4, # 11 ~ 13
|
|
329
|
+
np.nan, np.nan, np.nan, np.nan, # 14 ~ 17
|
|
330
|
+
1, 1, 1, 1, # 18 ~ 21
|
|
331
|
+
3, 4, 5, # 22 ~ 24
|
|
332
|
+
np.nan, np.nan, np.nan, np.nan, np.nan, # 25 ~ 29
|
|
333
|
+
1, 1, 1, 1, 1, 1, 1, # 30 ~ 36
|
|
334
|
+
np.nan, np.nan, np.nan # 37 ~ 39
|
|
335
|
+
]
|
|
336
|
+
)
|
|
337
|
+
result = rpu.get_section(
|
|
338
|
+
data,
|
|
339
|
+
repeat=4,
|
|
340
|
+
# mode='e', # 반복횟수 이상
|
|
341
|
+
# key='nan', # 최대 최소 범위 지정시 무시된다.
|
|
342
|
+
max_key=3, # 최대 3
|
|
343
|
+
min_key=2, # 최소 2
|
|
344
|
+
# between=True, # 사잇값
|
|
345
|
+
# max_equal=False, # 3 이하
|
|
346
|
+
# min_equal=True, # 2 이상
|
|
347
|
+
# except_nan=False, # 최대 최소 범위 지정시 무시된다.
|
|
348
|
+
# reverse=True # 반전 없음
|
|
349
|
+
)
|
|
350
|
+
print(result)
|
|
351
|
+
|
|
352
|
+
|
|
320
353
|
if __name__ == '__main__':
|
|
321
|
-
|
|
354
|
+
from utilskit import logutils as lu
|
|
355
|
+
log = lu.get_logger()
|
|
356
|
+
log.info('인포메이션')
|
|
357
|
+
log.error('에러로그')
|
|
358
|
+
main14()
|
|
@@ -0,0 +1,502 @@
|
|
|
1
|
+
import sys
|
|
2
|
+
import os
|
|
3
|
+
import numpy as np
|
|
4
|
+
import pandas as pd
|
|
5
|
+
import warnings
|
|
6
|
+
|
|
7
|
+
__all__ = ['get_section']
|
|
8
|
+
|
|
9
|
+
|
|
10
|
+
def issame(value1, value2):
|
|
11
|
+
# 서로 같은 경우
|
|
12
|
+
if value1 == value2:
|
|
13
|
+
return True
|
|
14
|
+
# 서로 다른 경우
|
|
15
|
+
else:
|
|
16
|
+
# 어느 한 쪽 이라도 str type 인 경우
|
|
17
|
+
if isinstance(value1, str) or isinstance(value2, str):
|
|
18
|
+
if str(value1) == str(value2):
|
|
19
|
+
return True # ex) value1 = 1, value2 = '1'
|
|
20
|
+
else:
|
|
21
|
+
return False # ex) value1 = 1, value2 = 'nan'
|
|
22
|
+
# 어느 한 쪽이라도 str type 이 아닌 경우
|
|
23
|
+
else:
|
|
24
|
+
# value1 이 NaN 일때
|
|
25
|
+
if np.isnan(value1):
|
|
26
|
+
# value2 도 NaN 이면
|
|
27
|
+
if np.isnan(value2):
|
|
28
|
+
return True
|
|
29
|
+
# value2 가 NaN 이 아니면
|
|
30
|
+
else:
|
|
31
|
+
return False
|
|
32
|
+
else:
|
|
33
|
+
return False
|
|
34
|
+
|
|
35
|
+
|
|
36
|
+
# def get_repeat_section2(data, repeat_num, refer_value=None, except_nan=True):
|
|
37
|
+
# '''
|
|
38
|
+
# '''
|
|
39
|
+
# raw_ary = np.array(data)
|
|
40
|
+
# ary = raw_ary.copy()
|
|
41
|
+
# same_tf = (ary[:-1] == ary[1:])
|
|
42
|
+
# is_nan = np.isnan(ary)
|
|
43
|
+
|
|
44
|
+
# for i, j, k, l in zip(ary[:-1], ary[1:], same_tf, is_nan):
|
|
45
|
+
# print(i, j, k, l)
|
|
46
|
+
|
|
47
|
+
# a = np.where(same_tf==1)
|
|
48
|
+
# print(a)
|
|
49
|
+
|
|
50
|
+
# sys.exit()
|
|
51
|
+
|
|
52
|
+
# value_list = []
|
|
53
|
+
# start_idx_list = []
|
|
54
|
+
# end_idx_list = []
|
|
55
|
+
# start_idx = 0
|
|
56
|
+
# # pre_value = 'nan'
|
|
57
|
+
# repeat_num = 1
|
|
58
|
+
# for idx, value in enumerate(ary):
|
|
59
|
+
|
|
60
|
+
# # 가장 처음인 경우
|
|
61
|
+
# if idx == 0:
|
|
62
|
+
# pre_value = value
|
|
63
|
+
# continue
|
|
64
|
+
|
|
65
|
+
# # 현재 값이 이전 값과 동일할때
|
|
66
|
+
# if issame(value, pre_value):
|
|
67
|
+
# repeat_num += 1
|
|
68
|
+
|
|
69
|
+
# # 현재 값이 이전 값과 다를때
|
|
70
|
+
# else:
|
|
71
|
+
# if repeat_num >= stan_repeat:
|
|
72
|
+
# value_list.append(pre_value)
|
|
73
|
+
# start_idx_list.append(start_idx)
|
|
74
|
+
# end_idx_list.append(idx-1)
|
|
75
|
+
# # 시작 지점 갱신 & 반복횟수 초기화
|
|
76
|
+
# start_idx = idx
|
|
77
|
+
# repeat_num = 1
|
|
78
|
+
# pre_value = value
|
|
79
|
+
|
|
80
|
+
# # 마지막 값이 이전 값과 같을때
|
|
81
|
+
# if issame(value, pre_value):
|
|
82
|
+
# if repeat_num >= stan_repeat:
|
|
83
|
+
# value_list.append(value)
|
|
84
|
+
# start_idx_list.append(start_idx)
|
|
85
|
+
# end_idx_list.append(idx)
|
|
86
|
+
# # --------------------------------------
|
|
87
|
+
# # 함수 수정중
|
|
88
|
+
# # 결과 정리
|
|
89
|
+
# result = {'nan':None}
|
|
90
|
+
# for v, si, ei in zip(value_list, start_idx_list, end_idx_list):
|
|
91
|
+
# result[str(v)] = (si, ei)
|
|
92
|
+
# if except_nan:
|
|
93
|
+
# del result['nan']
|
|
94
|
+
# return result
|
|
95
|
+
|
|
96
|
+
|
|
97
|
+
|
|
98
|
+
def get_repeat_section(data, repeat, except_nan=True):
|
|
99
|
+
'''
|
|
100
|
+
데이터 array 에서 정해놓은 반복 횟수 (stan_repeat) 만큼 반복되는 숫자구간이 있다면
|
|
101
|
+
그 구간의 시작, 끝 위치 index 값을 추출한다.
|
|
102
|
+
NaN 가 반복되는지 여부를 포함시킬 수 있다.
|
|
103
|
+
'''
|
|
104
|
+
ary = data.copy()
|
|
105
|
+
|
|
106
|
+
value_list = []
|
|
107
|
+
start_idx_list = []
|
|
108
|
+
end_idx_list = []
|
|
109
|
+
start_idx = 0
|
|
110
|
+
# pre_value = 'nan'
|
|
111
|
+
repeat_num = 1
|
|
112
|
+
for idx, value in enumerate(ary):
|
|
113
|
+
|
|
114
|
+
# 가장 처음인 경우
|
|
115
|
+
if idx == 0:
|
|
116
|
+
pre_value = value
|
|
117
|
+
continue
|
|
118
|
+
|
|
119
|
+
# 현재 값이 이전 값과 동일할때
|
|
120
|
+
if issame(value, pre_value):
|
|
121
|
+
repeat_num += 1
|
|
122
|
+
|
|
123
|
+
# 현재 값이 이전 값과 다를때
|
|
124
|
+
else:
|
|
125
|
+
if repeat_num >= repeat:
|
|
126
|
+
value_list.append(pre_value)
|
|
127
|
+
start_idx_list.append(start_idx)
|
|
128
|
+
end_idx_list.append(idx-1)
|
|
129
|
+
# 시작 지점 갱신 & 반복횟수 초기화
|
|
130
|
+
start_idx = idx
|
|
131
|
+
repeat_num = 1
|
|
132
|
+
|
|
133
|
+
pre_value = value
|
|
134
|
+
|
|
135
|
+
# 마지막 값이 이전 값과 같을때
|
|
136
|
+
if issame(value, pre_value):
|
|
137
|
+
if repeat_num >= repeat:
|
|
138
|
+
value_list.append(value)
|
|
139
|
+
start_idx_list.append(start_idx)
|
|
140
|
+
end_idx_list.append(idx)
|
|
141
|
+
# --------------------------------------
|
|
142
|
+
# 함수 수정중
|
|
143
|
+
# 결과 정리
|
|
144
|
+
# print(value_list)
|
|
145
|
+
# sys.exit()
|
|
146
|
+
result = {}
|
|
147
|
+
for v, si, ei in zip(value_list, start_idx_list, end_idx_list):
|
|
148
|
+
try:
|
|
149
|
+
result[str(v)].append((si, ei))
|
|
150
|
+
except KeyError:
|
|
151
|
+
result[str(v)] = [(si, ei)]
|
|
152
|
+
if except_nan:
|
|
153
|
+
del result['nan']
|
|
154
|
+
return result
|
|
155
|
+
|
|
156
|
+
|
|
157
|
+
def get_stan_repeat_section(data, value, repeat, mode='a', reverse=False):
|
|
158
|
+
'''
|
|
159
|
+
ary 에서 기준값(stan_value)이 지정한 횟수(stan_repeat)
|
|
160
|
+
이상(above) 또는 이하(below) 만큼 반복되는 구간의 시작, 끝 위치 index 값을 추출하는 함수
|
|
161
|
+
reverse 를 True 로 지정하면 해당 각 구간의 끝->시작, 시작->끝 으로 반전된다.
|
|
162
|
+
mode 는 a (above) 와 b (below)만 존재
|
|
163
|
+
'''
|
|
164
|
+
ary = data.copy()
|
|
165
|
+
|
|
166
|
+
start_idx = 0
|
|
167
|
+
start_idx_list = []
|
|
168
|
+
end_idx_list = []
|
|
169
|
+
repeat_num = 1
|
|
170
|
+
|
|
171
|
+
if len(ary) == 0:
|
|
172
|
+
return [], []
|
|
173
|
+
|
|
174
|
+
# stan_value = float(stan_value)
|
|
175
|
+
for idx, val_ in enumerate(ary):
|
|
176
|
+
|
|
177
|
+
# 가장 처음인 경우
|
|
178
|
+
if idx == 0:
|
|
179
|
+
pre_value = val_
|
|
180
|
+
continue
|
|
181
|
+
|
|
182
|
+
# 현재 값이 기준값(stan_value) 인 경우
|
|
183
|
+
if issame(val_, value):
|
|
184
|
+
# 이전값이 기준값과 동일하면
|
|
185
|
+
if issame(pre_value, value):
|
|
186
|
+
# 반복횟수 +1
|
|
187
|
+
repeat_num += 1
|
|
188
|
+
# 이전 값이 기준값과 다르면
|
|
189
|
+
else:
|
|
190
|
+
# 반복횟수 초기화
|
|
191
|
+
repeat_num = 1
|
|
192
|
+
# 현재 위치를 시작로 위치 지정
|
|
193
|
+
start_idx = idx
|
|
194
|
+
# 현재 값이 기준값과 다른 경우
|
|
195
|
+
else:
|
|
196
|
+
# 이전 값이 기준값과 동일하면
|
|
197
|
+
if issame(pre_value, value):
|
|
198
|
+
# idx 끝 위치 지정
|
|
199
|
+
|
|
200
|
+
# 반복 횟수 기준 이상인 경우
|
|
201
|
+
if mode == 'a':
|
|
202
|
+
# 기록된 반복 횟수가 기준 횟수 이상이면
|
|
203
|
+
if repeat_num >= repeat:
|
|
204
|
+
# 지정해둔 시작 위치 index 값을 구간시작 index 로 저장
|
|
205
|
+
start_idx_list.append(start_idx)
|
|
206
|
+
# 현재 위치 바로 이전 위치 index 값을 구간끝 index 로 저장
|
|
207
|
+
end_idx_list.append(idx-1)
|
|
208
|
+
# 반복 횟수 기준 이하인 경우
|
|
209
|
+
elif mode == 'b':
|
|
210
|
+
# 기록된 반복 횟수가 기준 횟수 이하면
|
|
211
|
+
if repeat_num <= repeat:
|
|
212
|
+
start_idx_list.append(start_idx)
|
|
213
|
+
end_idx_list.append(idx-1)
|
|
214
|
+
elif mode == 'e':
|
|
215
|
+
# 기록된 반복 횟수가 기준 횟수와 동일하면
|
|
216
|
+
if repeat_num == repeat:
|
|
217
|
+
start_idx_list.append(start_idx)
|
|
218
|
+
end_idx_list.append(idx-1)
|
|
219
|
+
else:
|
|
220
|
+
print('mode 를 a (above:이상), b (below:이하) 또는 e (equal:동일) 중 하나로 지정해주세요')
|
|
221
|
+
raise KeyError()
|
|
222
|
+
# 현재 위치 값을 이전 위치로 저장
|
|
223
|
+
pre_value = val_
|
|
224
|
+
|
|
225
|
+
# 가장 마지막 데이터가 기준값과 동일한 경우
|
|
226
|
+
if issame(val_, value):
|
|
227
|
+
if mode == 'a':
|
|
228
|
+
if repeat_num >= repeat:
|
|
229
|
+
start_idx_list.append(start_idx)
|
|
230
|
+
# 현재 위치 index 를 구간 끝 index 로 저장
|
|
231
|
+
end_idx_list.append(idx)
|
|
232
|
+
elif mode == 'b':
|
|
233
|
+
if repeat_num <= repeat:
|
|
234
|
+
start_idx_list.append(start_idx)
|
|
235
|
+
end_idx_list.append(idx)
|
|
236
|
+
elif mode == 'e':
|
|
237
|
+
if repeat_num == repeat:
|
|
238
|
+
start_idx_list.append(start_idx)
|
|
239
|
+
end_idx_list.append(idx)
|
|
240
|
+
else:
|
|
241
|
+
raise KeyError('mode 를 a (above:이상), b (below:이하) 또는 e (equal:동일) 중 하나로 지정해주세요')
|
|
242
|
+
# 가장 마지막 데이터가 기준값과 다르면 반복 계산할 필요 없음
|
|
243
|
+
|
|
244
|
+
# 반전
|
|
245
|
+
if reverse:
|
|
246
|
+
rev_start_idx_list = [0]
|
|
247
|
+
rev_end_idx_list = [len(ary)-1]
|
|
248
|
+
for ns_idx, ne_idx in zip(start_idx_list, end_idx_list):
|
|
249
|
+
if ns_idx == 0:
|
|
250
|
+
rev_start_idx_list.pop(0)
|
|
251
|
+
rev_start_idx_list.append(ne_idx+1)
|
|
252
|
+
continue
|
|
253
|
+
if ne_idx == len(ary)-1:
|
|
254
|
+
rev_end_idx_list.pop(-1)
|
|
255
|
+
rev_end_idx_list.append(ns_idx-1)
|
|
256
|
+
continue
|
|
257
|
+
rev_start_idx_list.append(ne_idx+1)
|
|
258
|
+
rev_end_idx_list.insert(-1, ns_idx-1)
|
|
259
|
+
|
|
260
|
+
start_idx_list = rev_start_idx_list.copy()
|
|
261
|
+
end_idx_list = rev_end_idx_list.copy()
|
|
262
|
+
|
|
263
|
+
# 결과 정리
|
|
264
|
+
result = []
|
|
265
|
+
for si, ei in zip(start_idx_list, end_idx_list):
|
|
266
|
+
result.append((si, ei))
|
|
267
|
+
|
|
268
|
+
return result
|
|
269
|
+
|
|
270
|
+
|
|
271
|
+
|
|
272
|
+
def reversing(data, start_idx_list, end_idx_list):
|
|
273
|
+
ary = data.copy()
|
|
274
|
+
# 반전
|
|
275
|
+
rev_start_idx_list = [0]
|
|
276
|
+
rev_end_idx_list = [len(ary)-1]
|
|
277
|
+
for ns_idx, ne_idx in zip(start_idx_list, end_idx_list):
|
|
278
|
+
if ns_idx == 0:
|
|
279
|
+
rev_start_idx_list.pop(0)
|
|
280
|
+
rev_start_idx_list.append(ne_idx+1)
|
|
281
|
+
continue
|
|
282
|
+
if ne_idx == len(ary)-1:
|
|
283
|
+
rev_end_idx_list.pop(-1)
|
|
284
|
+
rev_end_idx_list.append(ns_idx-1)
|
|
285
|
+
continue
|
|
286
|
+
rev_start_idx_list.append(ne_idx+1)
|
|
287
|
+
rev_end_idx_list.insert(-1, ns_idx-1)
|
|
288
|
+
|
|
289
|
+
start_idx_list = rev_start_idx_list.copy()
|
|
290
|
+
end_idx_list = rev_end_idx_list.copy()
|
|
291
|
+
|
|
292
|
+
# 결과 정리
|
|
293
|
+
result = []
|
|
294
|
+
for si, ei in zip(start_idx_list, end_idx_list):
|
|
295
|
+
result.append((si, ei))
|
|
296
|
+
|
|
297
|
+
return result
|
|
298
|
+
|
|
299
|
+
|
|
300
|
+
def get_section(data, repeat, mode='a', key=None,
|
|
301
|
+
max_key=None, min_key=None, between=False, max_equal=True, min_equal=True,
|
|
302
|
+
except_nan=True, reverse=False):
|
|
303
|
+
|
|
304
|
+
# ===============================================================
|
|
305
|
+
# 값 설정
|
|
306
|
+
|
|
307
|
+
# nan 설정 필터링
|
|
308
|
+
if str(key) == 'nan' and except_nan:
|
|
309
|
+
raise ValueError('연산결과에 NaN이 제외되어있습니다. NaN 의 구간을 산정하려면 except_nan 을 False 로 설정해주세요')
|
|
310
|
+
|
|
311
|
+
# 최소 2이상 반복 횟수 설정
|
|
312
|
+
if repeat <= 1:
|
|
313
|
+
raise ValueError('반복횟수(repeat)는 최소 2 이상을 입력해야합니다.')
|
|
314
|
+
|
|
315
|
+
# 최대값 기준 설정
|
|
316
|
+
if max_key is not None:
|
|
317
|
+
# key 값이 있는 경우 경고
|
|
318
|
+
if key is not None:
|
|
319
|
+
warnings.warn('max_key 또는 min_key 값이 설정되어있는 경우 key 값은 무시됩니다.')
|
|
320
|
+
# key 값을 무효화
|
|
321
|
+
key = None
|
|
322
|
+
# 기준값이 숫자가 아닌 경우
|
|
323
|
+
if not isinstance(max_key, (int, float)):
|
|
324
|
+
raise ValueError('최대값 기준은 숫자값(int, float)으로 입력해야합니다.')
|
|
325
|
+
# 사잇값이 아닌경우
|
|
326
|
+
if not between:
|
|
327
|
+
# 최댓값 이상인 값을 전부 최댓값으로 변환
|
|
328
|
+
if max_equal:
|
|
329
|
+
data = list(map(lambda x:max_key if x >= max_key else x, data))
|
|
330
|
+
# 최댓값 초과인 값을 전부 최댓값으로 변환
|
|
331
|
+
else:
|
|
332
|
+
data = list(map(lambda x:max_key+1 if x > max_key else x, data))
|
|
333
|
+
|
|
334
|
+
# 최소값 기준 설정
|
|
335
|
+
if min_key is not None:
|
|
336
|
+
# key 값이 있는 경우 경고
|
|
337
|
+
if key is not None:
|
|
338
|
+
warnings.warn('max_key 또는 min_key 값이 설정되어있는 경우 key 값은 무시됩니다.')
|
|
339
|
+
# key 값을 무효화
|
|
340
|
+
key = None
|
|
341
|
+
# 기준값이 숫자가 아닌 경우
|
|
342
|
+
if not isinstance(min_key, (int, float)):
|
|
343
|
+
raise ValueError('최소값 기준은 숫자값(int, float)으로 입력해야합니다.')
|
|
344
|
+
# 사잇값이 아닌 경우
|
|
345
|
+
if not between:
|
|
346
|
+
# 최솟값 이하인 값을 전부 최솟값으로 변환
|
|
347
|
+
if min_equal:
|
|
348
|
+
data = list(map(lambda x:min_key if x <= min_key else x, data))
|
|
349
|
+
else:
|
|
350
|
+
data = list(map(lambda x:min_key if x < min_key else x, data))
|
|
351
|
+
|
|
352
|
+
# 사잇값인 경우
|
|
353
|
+
if between:
|
|
354
|
+
# 최댓값 및 최솟값이 설정되어있는지 여부
|
|
355
|
+
if max_key is not None and min_key is not None:
|
|
356
|
+
# 최소~최대 사잇값을 전부 최소_최대 형태로 변환
|
|
357
|
+
if max_equal:
|
|
358
|
+
if min_equal:
|
|
359
|
+
data = list(map(lambda x:f'{min_key}_{max_key}' if x >= min_key and x <= max_key else x, data))
|
|
360
|
+
else:
|
|
361
|
+
data = list(map(lambda x:f'{min_key}_{max_key}' if x > min_key and x <= max_key else x, data))
|
|
362
|
+
else:
|
|
363
|
+
if min_equal:
|
|
364
|
+
data = list(map(lambda x:f'{min_key}_{max_key}' if x >= min_key and x < max_key else x, data))
|
|
365
|
+
else:
|
|
366
|
+
data = list(map(lambda x:f'{min_key}_{max_key}' if x > min_key and x < max_key else x, data))
|
|
367
|
+
|
|
368
|
+
else:
|
|
369
|
+
raise ValueError('between = True 로 설정한 경우 max_key 및 min_key 양쪽 다 값이 설정되어있어야합니다.')
|
|
370
|
+
# numpy array 화
|
|
371
|
+
data = np.array(data)
|
|
372
|
+
|
|
373
|
+
# key
|
|
374
|
+
# key 값의 형태를 데이터와 동일하게 설정
|
|
375
|
+
if key is not None:
|
|
376
|
+
key_df = pd.DataFrame([key, np.nan], columns=['key']).astype(str)
|
|
377
|
+
key = key_df['key'][0]
|
|
378
|
+
|
|
379
|
+
# =================================================================
|
|
380
|
+
# 반복 구간 판단
|
|
381
|
+
# data 라는 이름을 가진 string 열 생성
|
|
382
|
+
df = pd.DataFrame(data, columns=['data']).astype(str)
|
|
383
|
+
# 한 칸 앞으로 이동
|
|
384
|
+
df['data_next'] = df['data'].shift(-1)
|
|
385
|
+
# 한 칸 뒤로 이동
|
|
386
|
+
df['data_pre'] = df['data'].shift(1)
|
|
387
|
+
# 이전, 이후 간의 동일성을 기준으로 True, False 산정
|
|
388
|
+
df['next_tf'] = df['data'] == df['data_next']
|
|
389
|
+
df['pre_tf'] = df['data'] == df['data_pre']
|
|
390
|
+
# 값을 더하여 수치값으로 환산
|
|
391
|
+
df['tf'] = df['next_tf'].astype(int) + df['pre_tf'].astype(int)
|
|
392
|
+
'''
|
|
393
|
+
규칙상 1 에서 시작해서 1 로 끝나는 구간은 같은 값이 반복되는 구간임
|
|
394
|
+
1 과 1 의 사잇값은 반드시 2임
|
|
395
|
+
'''
|
|
396
|
+
|
|
397
|
+
# =================================================================
|
|
398
|
+
# 반복 구간 추출
|
|
399
|
+
data_ary = df['data'].values
|
|
400
|
+
tf_ary = df['tf'].values
|
|
401
|
+
result = {'nan':[]}
|
|
402
|
+
flag = 0
|
|
403
|
+
for idx, (d, tf) in enumerate(zip(data_ary, tf_ary)):
|
|
404
|
+
flag += tf
|
|
405
|
+
# 구간 시작
|
|
406
|
+
if tf == 1 and flag == 1:
|
|
407
|
+
start = idx
|
|
408
|
+
# 구간 끝
|
|
409
|
+
elif tf == 1 and flag >= 2:
|
|
410
|
+
# 반복횟수 계산
|
|
411
|
+
length = (flag+2) // 2
|
|
412
|
+
# 이상 모드
|
|
413
|
+
if mode == 'a':
|
|
414
|
+
if length >= repeat:
|
|
415
|
+
# 구간 저장
|
|
416
|
+
try: result[d].append((start, idx))
|
|
417
|
+
except KeyError: result[d] = [(start, idx)]
|
|
418
|
+
# 이하 모드
|
|
419
|
+
elif mode == 'b':
|
|
420
|
+
if length <= repeat:
|
|
421
|
+
# 구간 저장
|
|
422
|
+
try: result[d].append((start, idx))
|
|
423
|
+
except KeyError: result[d] = [(start, idx)]
|
|
424
|
+
# 동일 모드
|
|
425
|
+
elif mode == 'e':
|
|
426
|
+
if length == repeat:
|
|
427
|
+
# 구간 저장
|
|
428
|
+
try: result[d].append((start, idx))
|
|
429
|
+
except KeyError: result[d] = [(start, idx)]
|
|
430
|
+
# 모드 설정 에러
|
|
431
|
+
else:
|
|
432
|
+
raise KeyError('mode 를 a (above:이상), b (below:이하) 또는 e (equal:동일) 중 하나로 지정해주세요')
|
|
433
|
+
# 플래그 초기화
|
|
434
|
+
flag = 0
|
|
435
|
+
|
|
436
|
+
# =======================================================
|
|
437
|
+
# 최종 결과 필터링
|
|
438
|
+
|
|
439
|
+
# NaN 포함 여부
|
|
440
|
+
if except_nan:
|
|
441
|
+
del result['nan']
|
|
442
|
+
|
|
443
|
+
# 기준 키 값이 존재하는 경우
|
|
444
|
+
if key is not None:
|
|
445
|
+
try: result = {key : result[key]}
|
|
446
|
+
except KeyError:
|
|
447
|
+
result = {}
|
|
448
|
+
|
|
449
|
+
# 최대 설정이 존재하는 경우
|
|
450
|
+
new_result = {}
|
|
451
|
+
if max_key is not None:
|
|
452
|
+
# 사잇값이 아닌 경우
|
|
453
|
+
if not between:
|
|
454
|
+
for k, section in result.items():
|
|
455
|
+
if max_equal:
|
|
456
|
+
if float(k) >= max_key:
|
|
457
|
+
new_result[f'{k}_over'] = section
|
|
458
|
+
else:
|
|
459
|
+
if float(k) > max_key:
|
|
460
|
+
new_result[f'{float(k)-1}_over'] = section
|
|
461
|
+
del k, section
|
|
462
|
+
|
|
463
|
+
# 최소 설정이 존재하는 경우
|
|
464
|
+
if min_key is not None:
|
|
465
|
+
# 사잇값이 아닌 경우
|
|
466
|
+
if not between:
|
|
467
|
+
for k, section in result.items():
|
|
468
|
+
if min_equal:
|
|
469
|
+
if float(k) <= min_key:
|
|
470
|
+
new_result[f'{k}_under'] = section
|
|
471
|
+
else:
|
|
472
|
+
if float(k) < min_key:
|
|
473
|
+
new_result[f'{k}_under'] = section
|
|
474
|
+
del k, section
|
|
475
|
+
# 사잇값인 경우
|
|
476
|
+
if between and max_key is not None and min_key is not None:
|
|
477
|
+
for k, section in result.items():
|
|
478
|
+
if '_' in k:
|
|
479
|
+
try: new_result[f'{min_key}_{max_key}'] += section
|
|
480
|
+
except KeyError: new_result[f'{min_key}_{max_key}'] = section
|
|
481
|
+
del k, section
|
|
482
|
+
|
|
483
|
+
# 새로운 결과값이 존재하면
|
|
484
|
+
if min_key is not None or max_key is not None:
|
|
485
|
+
result = new_result
|
|
486
|
+
|
|
487
|
+
# 반전
|
|
488
|
+
rev_result = {}
|
|
489
|
+
if reverse:
|
|
490
|
+
for k, section_list in result.items():
|
|
491
|
+
start_idx_list = []
|
|
492
|
+
end_idx_list = []
|
|
493
|
+
for section in section_list:
|
|
494
|
+
start = section[0]
|
|
495
|
+
end = section[1]
|
|
496
|
+
start_idx_list.append(start)
|
|
497
|
+
end_idx_list.append(end)
|
|
498
|
+
rev_section = reversing(data, start_idx_list, end_idx_list)
|
|
499
|
+
rev_result[f'{k}_rev'] = rev_section
|
|
500
|
+
return rev_result
|
|
501
|
+
|
|
502
|
+
return result
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
Metadata-Version: 2.4
|
|
2
2
|
Name: utilskit
|
|
3
|
-
Version: 0.2.
|
|
3
|
+
Version: 0.2.1
|
|
4
4
|
Summary: description
|
|
5
5
|
Author: Kimyh
|
|
6
6
|
Author-email: kim_yh663927@naver.com
|
|
@@ -25,12 +25,14 @@ Dynamic: requires-dist
|
|
|
25
25
|
Dynamic: requires-python
|
|
26
26
|
Dynamic: summary
|
|
27
27
|
|
|
28
|
-
0.2.
|
|
28
|
+
# 0.2.1
|
|
29
|
+
- repeatutila 에 get_section 함수 추가
|
|
30
|
+
# 0.2.0
|
|
29
31
|
- 정식 최초 배포버전
|
|
30
32
|
- 각 함수의 사용성 강화 및 비활성 함수 지정
|
|
31
|
-
0.1.2
|
|
33
|
+
# 0.1.2
|
|
32
34
|
- repeatutils 의 get_repeat_section 에서 하나의 값이 여러 구간에서 반복될때 마지막 구간만 나오는 부분 수정
|
|
33
35
|
- repeatutils 의 get_repeat_section 및 get_stan_repeat_section 에서 추출되는 구간의 마지막 값이 +1 이 되는 부분 수정
|
|
34
|
-
0.1.1
|
|
35
|
-
repeatutils.py 추가
|
|
36
|
-
utils.py 에서 repeat 관련 함수 제거
|
|
36
|
+
# 0.1.1
|
|
37
|
+
- repeatutils.py 추가
|
|
38
|
+
- utils.py 에서 repeat 관련 함수 제거
|
|
@@ -1,267 +0,0 @@
|
|
|
1
|
-
import sys
|
|
2
|
-
import os
|
|
3
|
-
import numpy as np
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
__all__ = ['get_repeat_section', 'get_stan_repeat_section']
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
def issame(value1, value2):
|
|
10
|
-
# 서로 같은 경우
|
|
11
|
-
if value1 == value2:
|
|
12
|
-
return True
|
|
13
|
-
# 서로 다른 경우
|
|
14
|
-
else:
|
|
15
|
-
# 어느 한 쪽 이라도 str type 인 경우
|
|
16
|
-
if isinstance(value1, str) or isinstance(value2, str):
|
|
17
|
-
if str(value1) == str(value2):
|
|
18
|
-
return True # ex) value1 = 1, value2 = '1'
|
|
19
|
-
else:
|
|
20
|
-
return False # ex) value1 = 1, value2 = 'nan'
|
|
21
|
-
# 어느 한 쪽이라도 str type 이 아닌 경우
|
|
22
|
-
else:
|
|
23
|
-
# value1 이 NaN 일때
|
|
24
|
-
if np.isnan(value1):
|
|
25
|
-
# value2 도 NaN 이면
|
|
26
|
-
if np.isnan(value2):
|
|
27
|
-
return True
|
|
28
|
-
# value2 가 NaN 이 아니면
|
|
29
|
-
else:
|
|
30
|
-
return False
|
|
31
|
-
else:
|
|
32
|
-
return False
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
# def get_repeat_section2(data, repeat_num, refer_value=None, except_nan=True):
|
|
36
|
-
# '''
|
|
37
|
-
# '''
|
|
38
|
-
# raw_ary = np.array(data)
|
|
39
|
-
# ary = raw_ary.copy()
|
|
40
|
-
# same_tf = (ary[:-1] == ary[1:])
|
|
41
|
-
# is_nan = np.isnan(ary)
|
|
42
|
-
|
|
43
|
-
# for i, j, k, l in zip(ary[:-1], ary[1:], same_tf, is_nan):
|
|
44
|
-
# print(i, j, k, l)
|
|
45
|
-
|
|
46
|
-
# a = np.where(same_tf==1)
|
|
47
|
-
# print(a)
|
|
48
|
-
|
|
49
|
-
# sys.exit()
|
|
50
|
-
|
|
51
|
-
# value_list = []
|
|
52
|
-
# start_idx_list = []
|
|
53
|
-
# end_idx_list = []
|
|
54
|
-
# start_idx = 0
|
|
55
|
-
# # pre_value = 'nan'
|
|
56
|
-
# repeat_num = 1
|
|
57
|
-
# for idx, value in enumerate(ary):
|
|
58
|
-
|
|
59
|
-
# # 가장 처음인 경우
|
|
60
|
-
# if idx == 0:
|
|
61
|
-
# pre_value = value
|
|
62
|
-
# continue
|
|
63
|
-
|
|
64
|
-
# # 현재 값이 이전 값과 동일할때
|
|
65
|
-
# if issame(value, pre_value):
|
|
66
|
-
# repeat_num += 1
|
|
67
|
-
|
|
68
|
-
# # 현재 값이 이전 값과 다를때
|
|
69
|
-
# else:
|
|
70
|
-
# if repeat_num >= stan_repeat:
|
|
71
|
-
# value_list.append(pre_value)
|
|
72
|
-
# start_idx_list.append(start_idx)
|
|
73
|
-
# end_idx_list.append(idx-1)
|
|
74
|
-
# # 시작 지점 갱신 & 반복횟수 초기화
|
|
75
|
-
# start_idx = idx
|
|
76
|
-
# repeat_num = 1
|
|
77
|
-
# pre_value = value
|
|
78
|
-
|
|
79
|
-
# # 마지막 값이 이전 값과 같을때
|
|
80
|
-
# if issame(value, pre_value):
|
|
81
|
-
# if repeat_num >= stan_repeat:
|
|
82
|
-
# value_list.append(value)
|
|
83
|
-
# start_idx_list.append(start_idx)
|
|
84
|
-
# end_idx_list.append(idx)
|
|
85
|
-
# # --------------------------------------
|
|
86
|
-
# # 함수 수정중
|
|
87
|
-
# # 결과 정리
|
|
88
|
-
# result = {'nan':None}
|
|
89
|
-
# for v, si, ei in zip(value_list, start_idx_list, end_idx_list):
|
|
90
|
-
# result[str(v)] = (si, ei)
|
|
91
|
-
# if except_nan:
|
|
92
|
-
# del result['nan']
|
|
93
|
-
# return result
|
|
94
|
-
|
|
95
|
-
|
|
96
|
-
|
|
97
|
-
def get_repeat_section(data, repeat, except_nan=True):
|
|
98
|
-
'''
|
|
99
|
-
데이터 array 에서 정해놓은 반복 횟수 (stan_repeat) 만큼 반복되는 숫자구간이 있다면
|
|
100
|
-
그 구간의 시작, 끝 위치 index 값을 추출한다.
|
|
101
|
-
NaN 가 반복되는지 여부를 포함시킬 수 있다.
|
|
102
|
-
'''
|
|
103
|
-
ary = data.copy()
|
|
104
|
-
|
|
105
|
-
value_list = []
|
|
106
|
-
start_idx_list = []
|
|
107
|
-
end_idx_list = []
|
|
108
|
-
start_idx = 0
|
|
109
|
-
# pre_value = 'nan'
|
|
110
|
-
repeat_num = 1
|
|
111
|
-
for idx, value in enumerate(ary):
|
|
112
|
-
|
|
113
|
-
# 가장 처음인 경우
|
|
114
|
-
if idx == 0:
|
|
115
|
-
pre_value = value
|
|
116
|
-
continue
|
|
117
|
-
|
|
118
|
-
# 현재 값이 이전 값과 동일할때
|
|
119
|
-
if issame(value, pre_value):
|
|
120
|
-
repeat_num += 1
|
|
121
|
-
|
|
122
|
-
# 현재 값이 이전 값과 다를때
|
|
123
|
-
else:
|
|
124
|
-
if repeat_num >= repeat:
|
|
125
|
-
value_list.append(pre_value)
|
|
126
|
-
start_idx_list.append(start_idx)
|
|
127
|
-
end_idx_list.append(idx-1)
|
|
128
|
-
# 시작 지점 갱신 & 반복횟수 초기화
|
|
129
|
-
start_idx = idx
|
|
130
|
-
repeat_num = 1
|
|
131
|
-
|
|
132
|
-
pre_value = value
|
|
133
|
-
|
|
134
|
-
# 마지막 값이 이전 값과 같을때
|
|
135
|
-
if issame(value, pre_value):
|
|
136
|
-
if repeat_num >= repeat:
|
|
137
|
-
value_list.append(value)
|
|
138
|
-
start_idx_list.append(start_idx)
|
|
139
|
-
end_idx_list.append(idx)
|
|
140
|
-
# --------------------------------------
|
|
141
|
-
# 함수 수정중
|
|
142
|
-
# 결과 정리
|
|
143
|
-
# print(value_list)
|
|
144
|
-
# sys.exit()
|
|
145
|
-
result = {}
|
|
146
|
-
for v, si, ei in zip(value_list, start_idx_list, end_idx_list):
|
|
147
|
-
try:
|
|
148
|
-
result[str(v)].append((si, ei))
|
|
149
|
-
except KeyError:
|
|
150
|
-
result[str(v)] = [(si, ei)]
|
|
151
|
-
if except_nan:
|
|
152
|
-
del result['nan']
|
|
153
|
-
return result
|
|
154
|
-
|
|
155
|
-
|
|
156
|
-
def get_stan_repeat_section(data, value, repeat, mode='a', reverse=False):
|
|
157
|
-
'''
|
|
158
|
-
ary 에서 기준값(stan_value)이 지정한 횟수(stan_repeat)
|
|
159
|
-
이상(above) 또는 이하(below) 만큼 반복되는 구간의 시작, 끝 위치 index 값을 추출하는 함수
|
|
160
|
-
reverse 를 True 로 지정하면 해당 각 구간의 끝->시작, 시작->끝 으로 반전된다.
|
|
161
|
-
mode 는 a (above) 와 b (below)만 존재
|
|
162
|
-
'''
|
|
163
|
-
ary = data.copy()
|
|
164
|
-
|
|
165
|
-
start_idx = 0
|
|
166
|
-
start_idx_list = []
|
|
167
|
-
end_idx_list = []
|
|
168
|
-
repeat_num = 1
|
|
169
|
-
|
|
170
|
-
if len(ary) == 0:
|
|
171
|
-
return [], []
|
|
172
|
-
|
|
173
|
-
# stan_value = float(stan_value)
|
|
174
|
-
for idx, val_ in enumerate(ary):
|
|
175
|
-
|
|
176
|
-
# 가장 처음인 경우
|
|
177
|
-
if idx == 0:
|
|
178
|
-
pre_value = val_
|
|
179
|
-
continue
|
|
180
|
-
|
|
181
|
-
# 현재 값이 기준값(stan_value) 인 경우
|
|
182
|
-
if issame(val_, value):
|
|
183
|
-
# 이전값이 기준값과 동일하면
|
|
184
|
-
if issame(pre_value, value):
|
|
185
|
-
# 반복횟수 +1
|
|
186
|
-
repeat_num += 1
|
|
187
|
-
# 이전 값이 기준값과 다르면
|
|
188
|
-
else:
|
|
189
|
-
# 반복횟수 초기화
|
|
190
|
-
repeat_num = 1
|
|
191
|
-
# 현재 위치를 시작로 위치 지정
|
|
192
|
-
start_idx = idx
|
|
193
|
-
# 현재 값이 기준값과 다른 경우
|
|
194
|
-
else:
|
|
195
|
-
# 이전 값이 기준값과 동일하면
|
|
196
|
-
if issame(pre_value, value):
|
|
197
|
-
# idx 끝 위치 지정
|
|
198
|
-
|
|
199
|
-
# 반복 횟수 기준 이상인 경우
|
|
200
|
-
if mode == 'a':
|
|
201
|
-
# 기록된 반복 횟수가 기준 횟수 이상이면
|
|
202
|
-
if repeat_num >= repeat:
|
|
203
|
-
# 지정해둔 시작 위치 index 값을 구간시작 index 로 저장
|
|
204
|
-
start_idx_list.append(start_idx)
|
|
205
|
-
# 현재 위치 바로 이전 위치 index 값을 구간끝 index 로 저장
|
|
206
|
-
end_idx_list.append(idx-1)
|
|
207
|
-
# 반복 횟수 기준 이하인 경우
|
|
208
|
-
elif mode == 'b':
|
|
209
|
-
# 기록된 반복 횟수가 기준 횟수 이하면
|
|
210
|
-
if repeat_num <= repeat:
|
|
211
|
-
start_idx_list.append(start_idx)
|
|
212
|
-
end_idx_list.append(idx-1)
|
|
213
|
-
elif mode == 'e':
|
|
214
|
-
# 기록된 반복 횟수가 기준 횟수와 동일하면
|
|
215
|
-
if repeat_num == repeat:
|
|
216
|
-
start_idx_list.append(start_idx)
|
|
217
|
-
end_idx_list.append(idx-1)
|
|
218
|
-
else:
|
|
219
|
-
print('mode 를 a (above:이상), b (below:이하) 또는 e (equal:동일) 중 하나로 지정해주세요')
|
|
220
|
-
raise KeyError()
|
|
221
|
-
# 현재 위치 값을 이전 위치로 저장
|
|
222
|
-
pre_value = val_
|
|
223
|
-
|
|
224
|
-
# 가장 마지막 데이터가 기준값과 동일한 경우
|
|
225
|
-
if issame(val_, value):
|
|
226
|
-
if mode == 'a':
|
|
227
|
-
if repeat_num >= repeat:
|
|
228
|
-
start_idx_list.append(start_idx)
|
|
229
|
-
# 현재 위치 index 를 구간 끝 index 로 저장
|
|
230
|
-
end_idx_list.append(idx)
|
|
231
|
-
elif mode == 'b':
|
|
232
|
-
if repeat_num <= repeat:
|
|
233
|
-
start_idx_list.append(start_idx)
|
|
234
|
-
end_idx_list.append(idx)
|
|
235
|
-
elif mode == 'e':
|
|
236
|
-
if repeat_num == repeat:
|
|
237
|
-
start_idx_list.append(start_idx)
|
|
238
|
-
end_idx_list.append(idx)
|
|
239
|
-
else:
|
|
240
|
-
raise KeyError('mode 를 a (above:이상), b (below:이하) 또는 e (equal:동일) 중 하나로 지정해주세요')
|
|
241
|
-
# 가장 마지막 데이터가 기준값과 다르면 반복 계산할 필요 없음
|
|
242
|
-
|
|
243
|
-
# 반전
|
|
244
|
-
if reverse:
|
|
245
|
-
rev_start_idx_list = [0]
|
|
246
|
-
rev_end_idx_list = [len(ary)-1]
|
|
247
|
-
for ns_idx, ne_idx in zip(start_idx_list, end_idx_list):
|
|
248
|
-
if ns_idx == 0:
|
|
249
|
-
rev_start_idx_list.pop(0)
|
|
250
|
-
rev_start_idx_list.append(ne_idx+1)
|
|
251
|
-
continue
|
|
252
|
-
if ne_idx == len(ary)-1:
|
|
253
|
-
rev_end_idx_list.pop(-1)
|
|
254
|
-
rev_end_idx_list.append(ns_idx-1)
|
|
255
|
-
continue
|
|
256
|
-
rev_start_idx_list.append(ne_idx+1)
|
|
257
|
-
rev_end_idx_list.insert(-1, ns_idx-1)
|
|
258
|
-
|
|
259
|
-
start_idx_list = rev_start_idx_list.copy()
|
|
260
|
-
end_idx_list = rev_end_idx_list.copy()
|
|
261
|
-
|
|
262
|
-
# 결과 정리
|
|
263
|
-
result = []
|
|
264
|
-
for si, ei in zip(start_idx_list, end_idx_list):
|
|
265
|
-
result.append((si, ei))
|
|
266
|
-
|
|
267
|
-
return result
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|