hossam 0.4.3__py3-none-any.whl → 0.4.5__py3-none-any.whl

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.
hossam/hs_plot.py CHANGED
@@ -1,13 +1,14 @@
1
1
  # -*- coding: utf-8 -*-
2
2
  from __future__ import annotations
3
3
  from types import SimpleNamespace
4
+ from typing import Callable
4
5
 
5
6
  # ===================================================================
6
7
  import numpy as np
7
8
  import pandas as pd
8
9
  import seaborn as sb
9
10
  import matplotlib.pyplot as plt
10
- from matplotlib.pyplot import Axes
11
+ from matplotlib.pyplot import Axes # type: ignore
11
12
  from math import sqrt
12
13
  from pandas import DataFrame
13
14
 
@@ -15,7 +16,7 @@ from pandas import DataFrame
15
16
  from scipy.stats import t
16
17
  from scipy.spatial import ConvexHull
17
18
  from statsmodels.graphics.gofplots import qqplot as sm_qqplot
18
- from statsmodels.nonparametric.smoothers_lowess import lowess
19
+ from statsmodels.nonparametric.smoothers_lowess import lowess as sm_lowess
19
20
 
20
21
  # ===================================================================
21
22
  from statannotations.Annotator import Annotator
@@ -30,17 +31,14 @@ from sklearn.metrics import (
30
31
  )
31
32
 
32
33
  # ===================================================================
33
- if pd.__version__ > "2.0.0":
34
- pd.DataFrame.iteritems = pd.DataFrame.items
35
-
36
34
  config = SimpleNamespace(
37
35
  dpi=200,
38
- width=800,
39
- height=520,
40
- font_size=10,
36
+ width=600,
37
+ height=350,
38
+ font_size=7,
41
39
  font_weight="normal",
42
- frame_width=0.7,
43
- line_width=1.5,
40
+ frame_width=0.5,
41
+ line_width=1,
44
42
  grid_alpha=0.3,
45
43
  grid_width=0.5,
46
44
  fill_alpha=0.3
@@ -49,7 +47,7 @@ config = SimpleNamespace(
49
47
  # ===================================================================
50
48
  # 기본 크기가 설정된 Figure와 Axes를 생성한다
51
49
  # ===================================================================
52
- def get_default_ax(width: int = config.width, height: int = config.height, rows: int = 1, cols: int = 1, dpi: int = config.dpi, flatten: bool = False, ws: int | None = None, hs: int | None = None, title: str = None):
50
+ def get_default_ax(width: int = config.width, height: int = config.height, rows: int = 1, cols: int = 1, dpi: int = config.dpi, flatten: bool = False, ws: int | None = None, hs: int | None = None, title: str | None = None):
53
51
  """기본 크기의 Figure와 Axes를 생성한다.
54
52
 
55
53
  Args:
@@ -69,10 +67,13 @@ def get_default_ax(width: int = config.width, height: int = config.height, rows:
69
67
  figsize = (width * cols / 100, height * rows / 100)
70
68
  fig, ax = plt.subplots(rows, cols, figsize=figsize, dpi=dpi)
71
69
 
72
- if (rows > 1 or cols > 1) and (ws != None and hs != None):
70
+ # ax가 배열 (subplots)인지 단일 Axes인지 확인
71
+ is_array = isinstance(ax, (np.ndarray, list))
72
+
73
+ if is_array and (ws != None and hs != None):
73
74
  fig.subplots_adjust(wspace=ws, hspace=hs)
74
75
 
75
- if title:
76
+ if title and not is_array:
76
77
  fig.suptitle(title, fontsize=config.font_size * 1.5, fontweight='bold')
77
78
 
78
79
  if flatten == True:
@@ -92,7 +93,7 @@ def get_default_ax(width: int = config.width, height: int = config.height, rows:
92
93
  for spine in a.spines.values():
93
94
  spine.set_linewidth(config.frame_width)
94
95
  else:
95
- for spine in ax.spines.values():
96
+ for spine in ax.spines.values(): # type: ignore
96
97
  spine.set_linewidth(config.frame_width)
97
98
 
98
99
  return fig, ax
@@ -101,7 +102,7 @@ def get_default_ax(width: int = config.width, height: int = config.height, rows:
101
102
  # ===================================================================
102
103
  # 기본 크기가 설정된 Figure와 Axes를 생성한다
103
104
  # ===================================================================
104
- def create_figure(width: int = config.width, height: int = config.height, rows: int = 1, cols: int = 1, dpi: int = config.dpi, flatten: bool = False, ws: int | None = None, hs: int | None = None, title: str = None):
105
+ def create_figure(width: int = config.width, height: int = config.height, rows: int = 1, cols: int = 1, dpi: int = config.dpi, flatten: bool = False, ws: int | None = None, hs: int | None = None, title: str | None = None):
105
106
  """기본 크기의 Figure와 Axes를 생성한다. get_default_ax의 래퍼 함수.
106
107
 
107
108
  Args:
@@ -125,11 +126,11 @@ def create_figure(width: int = config.width, height: int = config.height, rows:
125
126
  # ===================================================================
126
127
  # 그래프의 그리드, 레이아웃을 정리하고 필요 시 저장 또는 표시한다
127
128
  # ===================================================================
128
- def finalize_plot(ax: Axes, callback: any = None, outparams: bool = False, save_path: str = None, grid: bool = True, title: str = None) -> None:
129
+ def finalize_plot(ax: Axes | np.ndarray, callback: Callable | None = None, outparams: bool = False, save_path: str | None = None, grid: bool = True, title: str | None = None) -> None:
129
130
  """공통 후처리를 수행한다: 콜백 실행, 레이아웃 정리, 필요 시 표시/종료.
130
131
 
131
132
  Args:
132
- ax (Axes|ndarray|list): 대상 Axes (단일 Axes 또는 subplots 배열).
133
+ ax (Axes|np.ndarray): 대상 Axes (단일 Axes 또는 subplots 배열).
133
134
  callback (Callable|None): 추가 설정을 위한 사용자 콜백.
134
135
  outparams (bool): 내부에서 생성한 Figure인 경우 True.
135
136
  save_path (str|None): 이미지 저장 경로. None이 아니면 해당 경로로 저장.
@@ -159,7 +160,7 @@ def finalize_plot(ax: Axes, callback: any = None, outparams: bool = False, save_
159
160
 
160
161
  plt.tight_layout()
161
162
 
162
- if title:
163
+ if title and not is_array:
163
164
  ax.set_title(title, fontsize=config.font_size * 1.3, pad=7, fontweight='bold')
164
165
 
165
166
  if save_path is not None:
@@ -173,12 +174,12 @@ def finalize_plot(ax: Axes, callback: any = None, outparams: bool = False, save_
173
174
  # ===================================================================
174
175
  # 그래프의 그리드, 레이아웃을 정리하고 필요 시 저장 또는 표시한다
175
176
  # ===================================================================
176
- def show_figure(ax: Axes, callback: any = None, outparams: bool = False, save_path: str = None, grid: bool = True, title: str = None) -> None:
177
+ def show_figure(ax: Axes | np.ndarray, callback: Callable | None = None, outparams: bool = False, save_path: str | None = None, grid: bool = True, title: str | None = None) -> None:
177
178
  """공통 후처리를 수행한다: 콜백 실행, 레이아웃 정리, 필요 시 표시/종료.
178
179
  finalize_plot의 래퍼 함수.
179
180
 
180
181
  Args:
181
- ax (Axes|ndarray|list): 대상 Axes (단일 Axes 또는 subplots 배열).
182
+ ax (Axes|np.ndarray): 대상 Axes (단일 Axes 또는 subplots 배열).
182
183
  callback (Callable|None): 추가 설정을 위한 사용자 콜백.
183
184
  outparams (bool): 내부에서 생성한 Figure인 경우 True.
184
185
  save_path (str|None): 이미지 저장 경로. None이 아니면 해당 경로로 저장.
@@ -196,19 +197,19 @@ def show_figure(ax: Axes, callback: any = None, outparams: bool = False, save_pa
196
197
  # ===================================================================
197
198
  def lineplot(
198
199
  df: DataFrame,
199
- xname: str = None,
200
- yname: str = None,
201
- hue: str = None,
200
+ xname: str | None = None,
201
+ yname: str | None = None,
202
+ hue: str | None = None,
202
203
  title: str | None = None,
203
- marker: str = None,
204
- palette: str = None,
204
+ marker: str | None = None,
205
+ palette: str | None = None,
205
206
  width: int = config.width,
206
207
  height: int = config.height,
207
208
  linewidth: float = config.line_width,
208
209
  dpi: int = config.dpi,
209
- save_path: str = None,
210
- callback: any = None,
211
- ax: Axes = None,
210
+ save_path: str | None = None,
211
+ callback: Callable | None = None,
212
+ ax: Axes | None = None,
212
213
  **params,
213
214
  ) -> None:
214
215
  """선 그래프를 그린다.
@@ -236,7 +237,7 @@ def lineplot(
236
237
  outparams = False
237
238
 
238
239
  if ax is None:
239
- fig, ax = get_default_ax(width, height, 1, 1, dpi)
240
+ fig, ax = get_default_ax(width, height, 1, 1, dpi) # type: ignore
240
241
  outparams = True
241
242
 
242
243
  # hue가 있을 때만 palette 사용, 없으면 color 사용
@@ -257,7 +258,7 @@ def lineplot(
257
258
  lineplot_kwargs.update(params)
258
259
 
259
260
  sb.lineplot(**lineplot_kwargs, linewidth=linewidth)
260
- finalize_plot(ax, callback, outparams, save_path, True, title)
261
+ finalize_plot(ax, callback, outparams, save_path, True, title) # type: ignore
261
262
 
262
263
 
263
264
  # ===================================================================
@@ -265,18 +266,18 @@ def lineplot(
265
266
  # ===================================================================
266
267
  def boxplot(
267
268
  df: DataFrame,
268
- xname: str = None,
269
- yname: str = None,
269
+ xname: str | None = None,
270
+ yname: str | None = None,
270
271
  title: str | None = None,
271
272
  orient: str = "v",
272
- palette: str = None,
273
+ palette: str | None = None,
273
274
  width: int = config.width,
274
275
  height: int = config.height,
275
276
  linewidth: float = config.line_width,
276
277
  dpi: int = config.dpi,
277
- save_path: str = None,
278
- callback: any = None,
279
- ax: Axes = None,
278
+ save_path: str | None = None,
279
+ callback: Callable | None = None,
280
+ ax: Axes | None = None,
280
281
  **params,
281
282
  ) -> None:
282
283
  """상자그림(boxplot)을 그린다.
@@ -303,7 +304,7 @@ def boxplot(
303
304
  outparams = False
304
305
 
305
306
  if ax is None:
306
- fig, ax = get_default_ax(width, height, 1, 1, dpi)
307
+ fig, ax = get_default_ax(width, height, 1, 1, dpi) # type: ignore
307
308
  outparams = True
308
309
 
309
310
  if xname is not None and yname is not None:
@@ -326,9 +327,9 @@ def boxplot(
326
327
  boxplot_kwargs.update(params)
327
328
  sb.boxplot(**boxplot_kwargs, linewidth=linewidth)
328
329
  else:
329
- sb.boxplot(data=df, orient=orient, ax=ax, linewidth=linewidth, **params)
330
+ sb.boxplot(data=df, orient=orient, ax=ax, linewidth=linewidth, **params) # type: ignore
330
331
 
331
- finalize_plot(ax, callback, outparams, save_path, True, title)
332
+ finalize_plot(ax, callback, outparams, save_path, True, title) # type: ignore
332
333
 
333
334
 
334
335
  # ===================================================================
@@ -336,11 +337,11 @@ def boxplot(
336
337
  # ===================================================================
337
338
  def kdeplot(
338
339
  df: DataFrame,
339
- xname: str = None,
340
- yname: str = None,
341
- hue: str = None,
340
+ xname: str | None = None,
341
+ yname: str | None = None,
342
+ hue: str | None = None,
342
343
  title: str | None = None,
343
- palette: str = None,
344
+ palette: str | None = None,
344
345
  fill: bool = False,
345
346
  fill_alpha: float = config.fill_alpha,
346
347
  linewidth: float = config.line_width,
@@ -348,9 +349,9 @@ def kdeplot(
348
349
  width: int = config.width,
349
350
  height: int = config.height,
350
351
  dpi: int = config.dpi,
351
- save_path: str = None,
352
- callback: any = None,
353
- ax: Axes = None,
352
+ save_path: str | None = None,
353
+ callback: Callable | None = None,
354
+ ax: Axes | None = None,
354
355
  **params,
355
356
  ) -> None:
356
357
  """커널 밀도 추정(KDE) 그래프를 그린다.
@@ -431,7 +432,7 @@ def kdeplot(
431
432
  return
432
433
 
433
434
  if ax is None:
434
- fig, ax = get_default_ax(width, height, 1, 1, dpi)
435
+ fig, ax = get_default_ax(width, height, 1, 1, dpi) # type: ignore
435
436
  outparams = True
436
437
 
437
438
  # 기본 kwargs 설정
@@ -461,7 +462,7 @@ def kdeplot(
461
462
 
462
463
  sb.kdeplot(**kdeplot_kwargs)
463
464
 
464
- finalize_plot(ax, callback, outparams, save_path, True, title)
465
+ finalize_plot(ax, callback, outparams, save_path, True, title) # type: ignore
465
466
 
466
467
 
467
468
  # ===================================================================
@@ -474,14 +475,14 @@ def histplot(
474
475
  title: str | None = None,
475
476
  bins: int | None = None,
476
477
  kde: bool = True,
477
- palette: str = None,
478
+ palette: str | None = None,
478
479
  width: int = config.width,
479
480
  height: int = config.height,
480
481
  linewidth: float = config.line_width,
481
482
  dpi: int = config.dpi,
482
- save_path: str = None,
483
- callback: any = None,
484
- ax: Axes = None,
483
+ save_path: str | None = None,
484
+ callback: Callable | None = None,
485
+ ax: Axes | None = None,
485
486
  **params,
486
487
  ) -> None:
487
488
  """히스토그램을 그리고 필요 시 KDE를 함께 표시한다.
@@ -508,7 +509,7 @@ def histplot(
508
509
  outparams = False
509
510
 
510
511
  if ax is None:
511
- fig, ax = get_default_ax(width, height, 1, 1, dpi)
512
+ fig, ax = get_default_ax(width, height, 1, 1, dpi) # type: ignore
512
513
  outparams = True
513
514
 
514
515
  if bins:
@@ -547,7 +548,7 @@ def histplot(
547
548
  histplot_kwargs.update(params)
548
549
  sb.histplot(**histplot_kwargs)
549
550
 
550
- finalize_plot(ax, callback, outparams, save_path, True, title)
551
+ finalize_plot(ax, callback, outparams, save_path, True, title) # type: ignore
551
552
 
552
553
 
553
554
  # ===================================================================
@@ -558,14 +559,14 @@ def stackplot(
558
559
  xname: str,
559
560
  hue: str,
560
561
  title: str | None = None,
561
- palette: str = None,
562
+ palette: str | None = None,
562
563
  width: int = config.width,
563
564
  height: int = config.height,
564
565
  linewidth: float = 0.25,
565
566
  dpi: int = config.dpi,
566
- save_path: str = None,
567
- callback: any = None,
568
- ax: Axes = None,
567
+ save_path: str | None = None,
568
+ callback: Callable | None = None,
569
+ ax: Axes | None = None,
569
570
  **params,
570
571
  ) -> None:
571
572
  """클래스 비율을 100% 누적 막대로 표현한다.
@@ -590,7 +591,7 @@ def stackplot(
590
591
  outparams = False
591
592
 
592
593
  if ax is None:
593
- fig, ax = get_default_ax(width, height, 1, 1, dpi)
594
+ fig, ax = get_default_ax(width, height, 1, 1, dpi) # type: ignore
594
595
  outparams = True
595
596
 
596
597
  df2 = df[[xname, hue]].copy()
@@ -617,11 +618,11 @@ def stackplot(
617
618
  sb.histplot(**stackplot_kwargs)
618
619
 
619
620
  # 그래프의 x축 항목 수 만큼 반복
620
- for p in ax.patches:
621
+ for p in ax.patches: # type: ignore
621
622
  # 각 막대의 위치, 넓이, 높이
622
- left, bottom, width, height = p.get_bbox().bounds
623
+ left, bottom, width, height = p.get_bbox().bounds # type: ignore
623
624
  # 막대의 중앙에 글자 표시하기
624
- ax.annotate(
625
+ ax.annotate( # type: ignore
625
626
  "%0.1f%%" % (height * 100),
626
627
  xy=(left + width / 2, bottom + height / 2),
627
628
  ha="center",
@@ -630,10 +631,10 @@ def stackplot(
630
631
 
631
632
  if str(df[xname].dtype) in ["int", "int32", "int64", "float", "float32", "float64"]:
632
633
  xticks = list(df[xname].unique())
633
- ax.set_xticks(xticks)
634
- ax.set_xticklabels(xticks)
634
+ ax.set_xticks(xticks) # type: ignore
635
+ ax.set_xticklabels(xticks) # type: ignore
635
636
 
636
- finalize_plot(ax, callback, outparams, save_path, True, title)
637
+ finalize_plot(ax, callback, outparams, save_path, True, title) # type: ignore
637
638
 
638
639
 
639
640
  # ===================================================================
@@ -645,14 +646,14 @@ def scatterplot(
645
646
  yname: str,
646
647
  hue=None,
647
648
  title: str | None = None,
648
- palette: str = None,
649
+ palette: str | None = None,
649
650
  width: int = config.width,
650
651
  height: int = config.height,
651
652
  linewidth: float = config.line_width,
652
653
  dpi: int = config.dpi,
653
- save_path: str = None,
654
- callback: any = None,
655
- ax: Axes = None,
654
+ save_path: str | None = None,
655
+ callback: Callable | None = None,
656
+ ax: Axes | None = None,
656
657
  **params,
657
658
  ) -> None:
658
659
  """산점도를 그린다.
@@ -678,7 +679,7 @@ def scatterplot(
678
679
  outparams = False
679
680
 
680
681
  if ax is None:
681
- fig, ax = get_default_ax(width, height, 1, 1, dpi)
682
+ fig, ax = get_default_ax(width, height, 1, 1, dpi) # type: ignore
682
683
  outparams = True
683
684
 
684
685
  # hue가 있을 때만 palette 사용, 없으면 color 사용
@@ -700,7 +701,7 @@ def scatterplot(
700
701
 
701
702
  sb.scatterplot(**scatterplot_kwargs)
702
703
 
703
- finalize_plot(ax, callback, outparams, save_path, True, title)
704
+ finalize_plot(ax, callback, outparams, save_path, True, title) # type: ignore
704
705
 
705
706
 
706
707
  # ===================================================================
@@ -711,14 +712,14 @@ def regplot(
711
712
  xname: str,
712
713
  yname: str,
713
714
  title: str | None = None,
714
- palette: str = None,
715
+ palette: str | None = None,
715
716
  width: int = config.width,
716
717
  height: int = config.height,
717
718
  linewidth: float = config.line_width,
718
719
  dpi: int = config.dpi,
719
- save_path: str = None,
720
- callback: any = None,
721
- ax: Axes = None,
720
+ save_path: str | None = None,
721
+ callback: Callable | None = None,
722
+ ax: Axes | None = None,
722
723
  **params,
723
724
  ) -> None:
724
725
  """단순 회귀선이 포함된 산점도를 그린다.
@@ -743,7 +744,7 @@ def regplot(
743
744
  outparams = False
744
745
 
745
746
  if ax is None:
746
- fig, ax = get_default_ax(width, height, 1, 1, dpi)
747
+ fig, ax = get_default_ax(width, height, 1, 1, dpi) # type: ignore
747
748
  outparams = True
748
749
 
749
750
  # regplot은 hue를 지원하지 않으므로 palette를 color로 변환
@@ -768,7 +769,7 @@ def regplot(
768
769
 
769
770
  sb.regplot(**regplot_kwargs)
770
771
 
771
- finalize_plot(ax, callback, outparams, save_path, True, title)
772
+ finalize_plot(ax, callback, outparams, save_path, True, title) # type: ignore
772
773
 
773
774
 
774
775
  # ===================================================================
@@ -780,12 +781,12 @@ def lmplot(
780
781
  yname: str,
781
782
  hue=None,
782
783
  title: str | None = None,
783
- palette: str = None,
784
+ palette: str | None = None,
784
785
  width: int = config.width,
785
786
  height: int = config.height,
786
787
  linewidth: float = config.line_width,
787
788
  dpi: int = config.dpi,
788
- save_path: str = None,
789
+ save_path: str | None = None,
789
790
  **params,
790
791
  ) -> None:
791
792
  """seaborn lmplot으로 선형 모델 시각화를 수행한다.
@@ -832,7 +833,7 @@ def lmplot(
832
833
  continue
833
834
  line.set_linewidth(linewidth)
834
835
 
835
- g.fig.grid(True, alpha=config.grid_alpha, linewidth=config.grid_width)
836
+ g.fig.grid(True, alpha=config.grid_alpha, linewidth=config.grid_width) # type: ignore
836
837
 
837
838
  if title:
838
839
  g.fig.suptitle(title, fontsize=config.font_size * 1.5, fontweight='bold')
@@ -855,12 +856,12 @@ def pairplot(
855
856
  title: str | None = None,
856
857
  diag_kind: str = "kde",
857
858
  hue=None,
858
- palette: str = None,
859
+ palette: str | None = None,
859
860
  width: int = config.height,
860
861
  height: int = config.height,
861
862
  linewidth: float = config.line_width,
862
863
  dpi: int = config.dpi,
863
- save_path: str = None,
864
+ save_path: str | None = None,
864
865
  **params,
865
866
  ) -> None:
866
867
  """연속형 변수의 숫자형 컬럼 쌍에 대한 관계를 그린다.
@@ -933,7 +934,7 @@ def pairplot(
933
934
  g.map_upper(func=sb.scatterplot, linewidth=linewidth)
934
935
 
935
936
  # KDE 대각선에도 linewidth 적용
936
- for ax in g.axes.diag:
937
+ for ax in g.axes.diag: # type: ignore
937
938
  for line in ax.get_lines():
938
939
  line.set_linewidth(linewidth)
939
940
 
@@ -954,15 +955,15 @@ def countplot(
954
955
  xname: str,
955
956
  hue=None,
956
957
  title: str | None = None,
957
- palette: str = None,
958
+ palette: str | None = None,
958
959
  order: int = 1,
959
960
  width: int = config.width,
960
961
  height: int = config.height,
961
962
  linewidth: float = config.line_width,
962
963
  dpi: int = config.dpi,
963
- save_path: str = None,
964
- callback: any = None,
965
- ax: Axes = None,
964
+ save_path: str | None = None,
965
+ callback: Callable | None = None,
966
+ ax: Axes | None = None,
966
967
  **params,
967
968
  ) -> None:
968
969
  """범주 빈도 막대그래프를 그린다.
@@ -994,7 +995,7 @@ def countplot(
994
995
  sort = sorted(list(df[xname].value_counts().index))
995
996
 
996
997
  if ax is None:
997
- fig, ax = get_default_ax(width, height, 1, 1, dpi)
998
+ fig, ax = get_default_ax(width, height, 1, 1, dpi) # type: ignore
998
999
  outparams = True
999
1000
 
1000
1001
  # hue가 있을 때만 palette 사용, 없으면 color 사용
@@ -1017,7 +1018,7 @@ def countplot(
1017
1018
 
1018
1019
  sb.countplot(**countplot_kwargs)
1019
1020
 
1020
- finalize_plot(ax, callback, outparams, save_path, True, title)
1021
+ finalize_plot(ax, callback, outparams, save_path, True, title) # type: ignore
1021
1022
 
1022
1023
 
1023
1024
  # ===================================================================
@@ -1029,14 +1030,14 @@ def barplot(
1029
1030
  yname: str,
1030
1031
  hue=None,
1031
1032
  title: str | None = None,
1032
- palette: str = None,
1033
+ palette: str | None = None,
1033
1034
  width: int = config.width,
1034
1035
  height: int = config.height,
1035
1036
  linewidth: float = config.line_width,
1036
1037
  dpi: int = config.dpi,
1037
- save_path: str = None,
1038
- callback: any = None,
1039
- ax: Axes = None,
1038
+ save_path: str | None = None,
1039
+ callback: Callable | None = None,
1040
+ ax: Axes | None = None,
1040
1041
  **params,
1041
1042
  ) -> None:
1042
1043
  """막대그래프를 그린다.
@@ -1062,7 +1063,7 @@ def barplot(
1062
1063
  outparams = False
1063
1064
 
1064
1065
  if ax is None:
1065
- fig, ax = get_default_ax(width, height, 1, 1, dpi)
1066
+ fig, ax = get_default_ax(width, height, 1, 1, dpi) # type: ignore
1066
1067
  outparams = True
1067
1068
 
1068
1069
  # hue가 있을 때만 palette 사용, 없으면 color 사용
@@ -1083,7 +1084,7 @@ def barplot(
1083
1084
  barplot_kwargs.update(params)
1084
1085
 
1085
1086
  sb.barplot(**barplot_kwargs)
1086
- finalize_plot(ax, callback, outparams, save_path, True, title)
1087
+ finalize_plot(ax, callback, outparams, save_path, True, title) # type: ignore
1087
1088
 
1088
1089
 
1089
1090
  # ===================================================================
@@ -1095,14 +1096,14 @@ def boxenplot(
1095
1096
  yname: str,
1096
1097
  hue=None,
1097
1098
  title: str | None = None,
1098
- palette: str = None,
1099
+ palette: str | None = None,
1099
1100
  width: int = config.width,
1100
1101
  height: int = config.height,
1101
1102
  linewidth: float = config.line_width,
1102
1103
  dpi: int = config.dpi,
1103
- save_path: str = None,
1104
- callback: any = None,
1105
- ax: Axes = None,
1104
+ save_path: str | None = None,
1105
+ callback: Callable | None = None,
1106
+ ax: Axes | None = None,
1106
1107
  **params,
1107
1108
  ) -> None:
1108
1109
  """박스앤 위스커 확장(boxen) 플롯을 그린다.
@@ -1128,7 +1129,7 @@ def boxenplot(
1128
1129
  outparams = False
1129
1130
 
1130
1131
  if ax is None:
1131
- fig, ax = get_default_ax(width, height, 1, 1, dpi)
1132
+ fig, ax = get_default_ax(width, height, 1, 1, dpi) # type: ignore
1132
1133
  outparams = True
1133
1134
 
1134
1135
  # palette은 hue가 있을 때만 사용
@@ -1147,7 +1148,7 @@ def boxenplot(
1147
1148
  boxenplot_kwargs.update(params)
1148
1149
 
1149
1150
  sb.boxenplot(**boxenplot_kwargs)
1150
- finalize_plot(ax, callback, outparams, save_path, True, title)
1151
+ finalize_plot(ax, callback, outparams, save_path, True, title) # type: ignore
1151
1152
 
1152
1153
 
1153
1154
  # ===================================================================
@@ -1159,14 +1160,14 @@ def violinplot(
1159
1160
  yname: str,
1160
1161
  hue=None,
1161
1162
  title: str | None = None,
1162
- palette: str = None,
1163
+ palette: str | None = None,
1163
1164
  width: int = config.width,
1164
1165
  height: int = config.height,
1165
1166
  linewidth: float = config.line_width,
1166
1167
  dpi: int = config.dpi,
1167
- save_path: str = None,
1168
- callback: any = None,
1169
- ax: Axes = None,
1168
+ save_path: str | None = None,
1169
+ callback: Callable | None = None,
1170
+ ax: Axes | None = None,
1170
1171
  **params,
1171
1172
  ) -> None:
1172
1173
  """바이올린 플롯을 그린다.
@@ -1192,7 +1193,7 @@ def violinplot(
1192
1193
  outparams = False
1193
1194
 
1194
1195
  if ax is None:
1195
- fig, ax = get_default_ax(width, height, 1, 1, dpi)
1196
+ fig, ax = get_default_ax(width, height, 1, 1, dpi) # type: ignore
1196
1197
  outparams = True
1197
1198
 
1198
1199
  # palette은 hue가 있을 때만 사용
@@ -1210,7 +1211,7 @@ def violinplot(
1210
1211
 
1211
1212
  violinplot_kwargs.update(params)
1212
1213
  sb.violinplot(**violinplot_kwargs)
1213
- finalize_plot(ax, callback, outparams, save_path, True, title)
1214
+ finalize_plot(ax, callback, outparams, save_path, True, title) # type: ignore
1214
1215
 
1215
1216
 
1216
1217
  # ===================================================================
@@ -1222,14 +1223,14 @@ def pointplot(
1222
1223
  yname: str,
1223
1224
  hue=None,
1224
1225
  title: str | None = None,
1225
- palette: str = None,
1226
+ palette: str | None = None,
1226
1227
  width: int = config.width,
1227
1228
  height: int = config.height,
1228
1229
  linewidth: float = config.line_width,
1229
1230
  dpi: int = config.dpi,
1230
- save_path: str = None,
1231
- callback: any = None,
1232
- ax: Axes = None,
1231
+ save_path: str | None = None,
1232
+ callback: Callable | None = None,
1233
+ ax: Axes | None = None,
1233
1234
  **params,
1234
1235
  ) -> None:
1235
1236
  """포인트 플롯을 그린다.
@@ -1255,7 +1256,7 @@ def pointplot(
1255
1256
  outparams = False
1256
1257
 
1257
1258
  if ax is None:
1258
- fig, ax = get_default_ax(width, height, 1, 1, dpi)
1259
+ fig, ax = get_default_ax(width, height, 1, 1, dpi) # type: ignore
1259
1260
  outparams = True
1260
1261
 
1261
1262
  # hue가 있을 때만 palette 사용, 없으면 color 사용
@@ -1275,7 +1276,7 @@ def pointplot(
1275
1276
 
1276
1277
  pointplot_kwargs.update(params)
1277
1278
  sb.pointplot(**pointplot_kwargs)
1278
- finalize_plot(ax, callback, outparams, save_path, True, title)
1279
+ finalize_plot(ax, callback, outparams, save_path, True, title) # type: ignore
1279
1280
 
1280
1281
 
1281
1282
  # ===================================================================
@@ -1287,12 +1288,12 @@ def jointplot(
1287
1288
  yname: str,
1288
1289
  hue=None,
1289
1290
  title: str | None = None,
1290
- palette: str = None,
1291
+ palette: str | None = None,
1291
1292
  width: int = config.width,
1292
1293
  height: int = config.height,
1293
1294
  linewidth: float = config.line_width,
1294
1295
  dpi: int = config.dpi,
1295
- save_path: str = None,
1296
+ save_path: str | None = None,
1296
1297
  **params,
1297
1298
  ) -> None:
1298
1299
  """공동 분포(joint) 플롯을 그린다.
@@ -1355,14 +1356,14 @@ def jointplot(
1355
1356
  def heatmap(
1356
1357
  data: DataFrame,
1357
1358
  title: str | None = None,
1358
- palette: str = None,
1359
+ palette: str | None = None,
1359
1360
  width: int | None = None,
1360
1361
  height: int | None = None,
1361
1362
  linewidth: float = 0.25,
1362
1363
  dpi: int = config.dpi,
1363
- save_path: str = None,
1364
- callback: any = None,
1365
- ax: Axes = None,
1364
+ save_path: str | None = None,
1365
+ callback: Callable | None = None,
1366
+ ax: Axes | None = None,
1366
1367
  **params,
1367
1368
  ) -> None:
1368
1369
  """히트맵을 그린다(값 주석 포함).
@@ -1386,10 +1387,10 @@ def heatmap(
1386
1387
 
1387
1388
  if width == None or height == None:
1388
1389
  width = (config.font_size * config.dpi / 72) * 4.5 * len(data.columns)
1389
- height = width * 0.8
1390
+ height = width * 0.8 # type: ignore
1390
1391
 
1391
1392
  if ax is None:
1392
- fig, ax = get_default_ax(width, height, 1, 1, dpi)
1393
+ fig, ax = get_default_ax(width, height, 1, 1, dpi) # type: ignore
1393
1394
  outparams = True
1394
1395
 
1395
1396
  heatmatp_kwargs = {
@@ -1407,26 +1408,26 @@ def heatmap(
1407
1408
  # heatmap은 hue를 지원하지 않으므로 cmap에 palette 사용
1408
1409
  sb.heatmap(**heatmatp_kwargs)
1409
1410
 
1410
- finalize_plot(ax, callback, outparams, save_path, True, title)
1411
+ finalize_plot(ax, callback, outparams, save_path, True, title) # type: ignore
1411
1412
 
1412
1413
 
1413
1414
  # ===================================================================
1414
- # 클러스터별 볼록 ꯐ막(convex hull)을 그린다
1415
+ # 클러스터별 볼록 경계막(convex hull)을 그린다
1415
1416
  # ===================================================================
1416
1417
  def convex_hull(
1417
1418
  data: DataFrame,
1418
1419
  xname: str,
1419
1420
  yname: str,
1420
- hue: str,
1421
+ hue: str | None = None,
1421
1422
  title: str | None = None,
1422
- palette: str = None,
1423
+ palette: str | None = None,
1423
1424
  width: int = config.width,
1424
1425
  height: int = config.height,
1425
1426
  linewidth: float = config.line_width,
1426
1427
  dpi: int = config.dpi,
1427
- save_path: str = None,
1428
- callback: any = None,
1429
- ax: Axes = None,
1428
+ save_path: str | None = None,
1429
+ callback: Callable | None = None,
1430
+ ax: Axes | None = None,
1430
1431
  **params,
1431
1432
  ):
1432
1433
  """클러스터별 볼록 껍질(convex hull)과 산점도를 그린다.
@@ -1452,7 +1453,7 @@ def convex_hull(
1452
1453
  outparams = False
1453
1454
 
1454
1455
  if ax is None:
1455
- fig, ax = get_default_ax(width, height, 1, 1, dpi)
1456
+ fig, ax = get_default_ax(width, height, 1, 1, dpi) # type: ignore
1456
1457
  outparams = True
1457
1458
 
1458
1459
  # 군집별 값의 종류별로 반복 수행
@@ -1470,10 +1471,10 @@ def convex_hull(
1470
1471
  # 마지막 좌표 이후에 첫 번째 좌표를 연결
1471
1472
  points = np.append(hull.vertices, hull.vertices[0])
1472
1473
 
1473
- ax.plot(
1474
+ ax.plot( # type: ignore
1474
1475
  df_c.iloc[points, 0], df_c.iloc[points, 1], linewidth=linewidth, linestyle=":"
1475
1476
  )
1476
- ax.fill(df_c.iloc[points, 0], df_c.iloc[points, 1], alpha=0.1)
1477
+ ax.fill(df_c.iloc[points, 0], df_c.iloc[points, 1], alpha=0.1) # type: ignore
1477
1478
  except:
1478
1479
  pass
1479
1480
 
@@ -1481,7 +1482,7 @@ def convex_hull(
1481
1482
  sb.scatterplot(
1482
1483
  data=data, x=xname, y=yname, hue=hue, palette=palette, ax=ax, **params
1483
1484
  )
1484
- finalize_plot(ax, callback, outparams, save_path, True, title)
1485
+ finalize_plot(ax, callback, outparams, save_path, True, title) # type: ignore
1485
1486
 
1486
1487
 
1487
1488
  # ===================================================================
@@ -1497,9 +1498,9 @@ def kde_confidence_interval(
1497
1498
  linewidth: float = config.line_width,
1498
1499
  fill: bool = False,
1499
1500
  dpi: int = config.dpi,
1500
- save_path: str = None,
1501
- callback: any = None,
1502
- ax: Axes = None,
1501
+ save_path: str | None = None,
1502
+ callback: Callable | None = None,
1503
+ ax: Axes | None = None,
1503
1504
  ) -> None:
1504
1505
  """각 숫자 컬럼에 대해 KDE와 t-분포 기반 신뢰구간을 그린다.
1505
1506
 
@@ -1569,7 +1570,7 @@ def kde_confidence_interval(
1569
1570
  cmin, cmax = t.interval(clevel, dof, loc=sample_mean, scale=sample_std_error)
1570
1571
 
1571
1572
  # 현재 컬럼에 대한 커널밀도추정
1572
- sb.kdeplot(data=column, linewidth=linewidth, ax=current_ax, fill=fill, alpha=config.fill_alpha)
1573
+ sb.kdeplot(data=column, linewidth=linewidth, ax=current_ax, fill=fill, alpha=config.fill_alpha) # type: ignore
1573
1574
 
1574
1575
  # 그래프 축의 범위
1575
1576
  xmin, xmax, ymin, ymax = current_ax.get_position().bounds
@@ -1594,7 +1595,7 @@ def kde_confidence_interval(
1594
1595
 
1595
1596
  current_ax.grid(True, alpha=config.grid_alpha, linewidth=config.grid_width)
1596
1597
 
1597
- finalize_plot(axes[0] if isinstance(axes, list) and len(axes) > 0 else ax, callback, outparams, save_path, True, title)
1598
+ finalize_plot(axes[0] if isinstance(axes, list) and len(axes) > 0 else ax, callback, outparams, save_path, True, title) # type: ignore
1598
1599
 
1599
1600
 
1600
1601
  # ===================================================================
@@ -1605,7 +1606,7 @@ def pvalue1_anotation(
1605
1606
  target: str,
1606
1607
  hue: str,
1607
1608
  title: str | None = None,
1608
- pairs: list = None,
1609
+ pairs: list | None = None,
1609
1610
  test: str = "t-test_ind",
1610
1611
  text_format: str = "star",
1611
1612
  loc: str = "outside",
@@ -1613,9 +1614,9 @@ def pvalue1_anotation(
1613
1614
  height: int = config.height,
1614
1615
  linewidth: float = config.line_width,
1615
1616
  dpi: int = config.dpi,
1616
- save_path: str = None,
1617
- callback: any = None,
1618
- ax: Axes = None,
1617
+ save_path: str | None = None,
1618
+ callback: Callable | None = None,
1619
+ ax: Axes | None = None,
1619
1620
  **params
1620
1621
  ) -> None:
1621
1622
  """statannotations를 이용해 상자그림에 p-value 주석을 추가한다.
@@ -1649,7 +1650,7 @@ def pvalue1_anotation(
1649
1650
  outparams = False
1650
1651
 
1651
1652
  if ax is None:
1652
- fig, ax = get_default_ax(width, height, 1, 1, dpi)
1653
+ fig, ax = get_default_ax(width, height, 1, 1, dpi) # type: ignore
1653
1654
  outparams = True
1654
1655
 
1655
1656
  # params에서 palette 추출 (있으면)
@@ -1676,7 +1677,7 @@ def pvalue1_anotation(
1676
1677
  annotator.apply_and_annotate()
1677
1678
 
1678
1679
  sb.despine()
1679
- finalize_plot(ax, callback, outparams, save_path, True, title)
1680
+ finalize_plot(ax, callback, outparams, save_path, True, title) # type: ignore
1680
1681
 
1681
1682
 
1682
1683
 
@@ -1692,9 +1693,9 @@ def ols_residplot(
1692
1693
  height: int = config.height,
1693
1694
  linewidth: float = config.line_width,
1694
1695
  dpi: int = config.dpi,
1695
- save_path: str = None,
1696
- callback: any = None,
1697
- ax: Axes = None,
1696
+ save_path: str | None = None,
1697
+ callback: Callable | None = None,
1698
+ ax: Axes | None = None,
1698
1699
  **params,
1699
1700
  ) -> None:
1700
1701
  """잔차도를 그린다(선택적으로 MSE 범위와 LOWESS 포함).
@@ -1736,24 +1737,23 @@ def ols_residplot(
1736
1737
  y = y_pred + resid # 실제값 = 적합값 + 잔차
1737
1738
 
1738
1739
  if ax is None:
1739
- fig, ax = get_default_ax(width, height, 1, 1, dpi)
1740
+ fig, ax = get_default_ax(width + 150 if mse else width, height, 1, 1, dpi) # type: ignore
1740
1741
  outparams = True
1741
1742
 
1742
- # 산점도 직접 그리기 (seaborn.residplot보다 훨씬 빠름)
1743
- ax.scatter(y_pred, resid, edgecolor="white", alpha=0.7, **params)
1743
+ # 산점도 seaborn으로 그리기
1744
+ sb.scatterplot(x=y_pred, y=resid, ax=ax, s=0.5, edgecolor="white", alpha=config.fill_alpha, **params)
1744
1745
 
1745
1746
  # 기준선 (잔차 = 0)
1746
- ax.axhline(0, color="gray", linestyle="--", linewidth=linewidth)
1747
+ ax.axhline(0, color="gray", linestyle="--", linewidth=linewidth*0.7) # type: ignore
1747
1748
 
1748
1749
  # LOWESS 스무딩 (선택적)
1749
1750
  if lowess:
1750
- from statsmodels.nonparametric.smoothers_lowess import lowess as sm_lowess
1751
1751
  lowess_result = sm_lowess(resid, y_pred, frac=0.6667)
1752
- ax.plot(lowess_result[:, 0], lowess_result[:, 1],
1753
- color="red", linewidth=linewidth, label="LOWESS")
1752
+ ax.plot(lowess_result[:, 0], lowess_result[:, 1], # type: ignore
1753
+ color="red", linewidth=linewidth, label="LOWESS") # type: ignore
1754
1754
 
1755
- ax.set_xlabel("Fitted values")
1756
- ax.set_ylabel("Residuals")
1755
+ ax.set_xlabel("Fitted values") # type: ignore
1756
+ ax.set_ylabel("Residuals") # type: ignore
1757
1757
 
1758
1758
  if mse:
1759
1759
  mse_val = mean_squared_error(y, y_pred)
@@ -1773,40 +1773,40 @@ def ols_residplot(
1773
1773
 
1774
1774
  mse_r = [r1, r2, r3]
1775
1775
 
1776
- xmin, xmax = ax.get_xlim()
1776
+ xmin, xmax = ax.get_xlim() # type: ignore
1777
1777
 
1778
1778
  # 구간별 반투명 색상 채우기 (안쪽부터 바깥쪽으로, 진한 색에서 연한 색으로)
1779
1779
  colors = ["red", "green", "blue"]
1780
1780
  alphas = [0.15, 0.10, 0.05] # 안쪽이 더 진하게
1781
1781
 
1782
1782
  # 3σ 영역 (가장 바깥쪽, 가장 연함)
1783
- ax.axhspan(-3 * mse_sq, 3 * mse_sq, facecolor=colors[2], alpha=alphas[2], zorder=0)
1783
+ ax.axhspan(-3 * mse_sq, 3 * mse_sq, facecolor=colors[2], alpha=alphas[2], zorder=0) # type: ignore
1784
1784
  # 2σ 영역 (중간)
1785
- ax.axhspan(-2 * mse_sq, 2 * mse_sq, facecolor=colors[1], alpha=alphas[1], zorder=1)
1785
+ ax.axhspan(-2 * mse_sq, 2 * mse_sq, facecolor=colors[1], alpha=alphas[1], zorder=1) # type: ignore
1786
1786
  # 1σ 영역 (가장 안쪽, 가장 진함)
1787
- ax.axhspan(-mse_sq, mse_sq, facecolor=colors[0], alpha=alphas[0], zorder=2)
1787
+ ax.axhspan(-mse_sq, mse_sq, facecolor=colors[0], alpha=alphas[0], zorder=2) # type: ignore
1788
1788
 
1789
1789
  # 경계선 그리기
1790
1790
  for i, c in enumerate(["red", "green", "blue"]):
1791
- ax.axhline(mse_sq * (i + 1), color=c, linestyle="--", linewidth=linewidth/2)
1792
- ax.axhline(mse_sq * (-(i + 1)), color=c, linestyle="--", linewidth=linewidth/2)
1791
+ ax.axhline(mse_sq * (i + 1), color=c, linestyle="--", linewidth=linewidth/2) # type: ignore
1792
+ ax.axhline(mse_sq * (-(i + 1)), color=c, linestyle="--", linewidth=linewidth/2) # type: ignore
1793
1793
 
1794
1794
  target = [68, 95, 99.7]
1795
1795
  for i, c in enumerate(["red", "green", "blue"]):
1796
- ax.text(
1796
+ ax.text( # type: ignore
1797
1797
  s=f"{i+1} sqrt(MSE) = {mse_r[i]:.2f}% ({mse_r[i] - target[i]:.2f}%)",
1798
1798
  x=xmax + 0.2,
1799
1799
  y=(i + 1) * mse_sq,
1800
1800
  color=c,
1801
1801
  )
1802
- ax.text(
1802
+ ax.text( # type: ignore
1803
1803
  s=f"-{i+1} sqrt(MSE) = {mse_r[i]:.2f}% ({mse_r[i] - target[i]:.2f}%)",
1804
1804
  x=xmax + 0.2,
1805
1805
  y=-(i + 1) * mse_sq,
1806
1806
  color=c,
1807
1807
  )
1808
1808
 
1809
- finalize_plot(ax, callback, outparams, save_path, True, title)
1809
+ finalize_plot(ax, callback, outparams, save_path, True, title) # type: ignore
1810
1810
 
1811
1811
 
1812
1812
  # ===================================================================
@@ -1820,9 +1820,9 @@ def ols_qqplot(
1820
1820
  height: int = config.height,
1821
1821
  linewidth: float = config.line_width,
1822
1822
  dpi: int = config.dpi,
1823
- save_path: str = None,
1824
- callback: any = None,
1825
- ax: Axes = None,
1823
+ save_path: str | None = None,
1824
+ callback: Callable | None = None,
1825
+ ax: Axes | None = None,
1826
1826
  **params,
1827
1827
  ) -> None:
1828
1828
  """표준화된 잔차의 정규성 확인을 위한 QQ 플롯을 그린다.
@@ -1867,7 +1867,7 @@ def ols_qqplot(
1867
1867
  outparams = False
1868
1868
 
1869
1869
  if ax is None:
1870
- fig, ax = get_default_ax(width, height, 1, 1, dpi)
1870
+ fig, ax = get_default_ax(width, height, 1, 1, dpi) # type: ignore
1871
1871
  outparams = True
1872
1872
 
1873
1873
  # fit 객체에서 잔차(residuals) 추출
@@ -1882,7 +1882,7 @@ def ols_qqplot(
1882
1882
  sm_qqplot(residuals, line=line, ax=ax, **params)
1883
1883
 
1884
1884
  # 점의 스타일 개선: 연한 내부, 진한 테두리
1885
- for collection in ax.collections:
1885
+ for collection in ax.collections: # type: ignore
1886
1886
  # PathCollection (scatter plot의 점들)
1887
1887
  collection.set_facecolor('#4A90E2') # 연한 파란색 내부
1888
1888
  collection.set_edgecolor('#1E3A8A') # 진한 파란색 테두리
@@ -1890,11 +1890,11 @@ def ols_qqplot(
1890
1890
  collection.set_alpha(0.7) # 약간의 투명도
1891
1891
 
1892
1892
  # 선 굵기 조정
1893
- for line in ax.get_lines():
1894
- if line.get_linestyle() == '--' or line.get_color() == 'r':
1895
- line.set_linewidth(linewidth)
1893
+ for line in ax.get_lines(): # type: ignore
1894
+ if line.get_linestyle() == '--' or line.get_color() == 'r': # type: ignore
1895
+ line.set_linewidth(linewidth) # type: ignore
1896
1896
 
1897
- finalize_plot(ax, callback, outparams, save_path, True, title)
1897
+ finalize_plot(ax, callback, outparams, save_path, True, title) # type: ignore
1898
1898
 
1899
1899
 
1900
1900
  # ===================================================================
@@ -1903,18 +1903,18 @@ def ols_qqplot(
1903
1903
  def distribution_by_class(
1904
1904
  data: DataFrame,
1905
1905
  title: str | None = None,
1906
- xnames: list = None,
1907
- hue: str = None,
1906
+ xnames: list | None = None,
1907
+ hue: str | None = None,
1908
1908
  type: str = "kde",
1909
- bins: any = 5,
1910
- palette: str = None,
1909
+ bins: list[int] | int = 5,
1910
+ palette: str | None = None,
1911
1911
  fill: bool = False,
1912
1912
  width: int = config.width,
1913
1913
  height: int = config.height,
1914
1914
  linewidth: float = config.line_width,
1915
1915
  dpi: int = config.dpi,
1916
- save_path: str = None,
1917
- callback: any = None,
1916
+ save_path: str | None = None,
1917
+ callback: Callable | None = None,
1918
1918
  ) -> None:
1919
1919
  """클래스별로 각 숫자형 특징의 분포를 KDE 또는 히스토그램으로 그린다.
1920
1920
 
@@ -1937,9 +1937,9 @@ def distribution_by_class(
1937
1937
  None
1938
1938
  """
1939
1939
  if xnames is None:
1940
- xnames = data.columns
1940
+ xnames = data.columns # type: ignore
1941
1941
 
1942
- for i, v in enumerate(xnames):
1942
+ for i, v in enumerate(xnames): # type: ignore
1943
1943
  # 종속변수이거나 숫자형이 아닌 경우는 제외
1944
1944
  if v == hue or data[v].dtype not in [
1945
1945
  "int",
@@ -1970,7 +1970,7 @@ def distribution_by_class(
1970
1970
  df=data,
1971
1971
  xname=v,
1972
1972
  hue=hue,
1973
- bins=bins,
1973
+ bins=bins, # type: ignore
1974
1974
  kde=False,
1975
1975
  palette=palette,
1976
1976
  width=width,
@@ -1985,7 +1985,7 @@ def distribution_by_class(
1985
1985
  df=data,
1986
1986
  xname=v,
1987
1987
  hue=hue,
1988
- bins=bins,
1988
+ bins=bins, # type: ignore
1989
1989
  kde=True,
1990
1990
  palette=palette,
1991
1991
  width=width,
@@ -2012,8 +2012,8 @@ def scatter_by_class(
2012
2012
  height: int = config.height,
2013
2013
  linewidth: float = config.line_width,
2014
2014
  dpi: int = config.dpi,
2015
- save_path: str = None,
2016
- callback: any = None,
2015
+ save_path: str | None = None,
2016
+ callback: Callable | None = None,
2017
2017
  ) -> None:
2018
2018
  """종속변수(y)와 각 연속형 독립변수(x) 간 산점도/볼록껍질을 그린다.
2019
2019
 
@@ -2068,7 +2068,7 @@ def scatter_by_class(
2068
2068
  for v in group:
2069
2069
  scatterplot(data=data, xname=v[0], yname=v[1], hue=hue, palette=palette,
2070
2070
  width=width, height=height, linewidth=linewidth, dpi=dpi, callback=callback,
2071
- save_path=save_path)
2071
+ save_path=save_path) # type: ignore
2072
2072
 
2073
2073
 
2074
2074
  # ===================================================================
@@ -2087,8 +2087,8 @@ def categorical_target_distribution(
2087
2087
  linewidth: float = config.line_width,
2088
2088
  dpi: int = config.dpi,
2089
2089
  cols: int = 2,
2090
- save_path: str = None,
2091
- callback: any = None,
2090
+ save_path: str | None = None,
2091
+ callback: Callable | None = None,
2092
2092
  ) -> None:
2093
2093
  """명목형 변수별로 종속변수 분포 차이를 시각화한다.
2094
2094
 
@@ -2163,16 +2163,16 @@ def categorical_target_distribution(
2163
2163
  # ===================================================================
2164
2164
  def roc_curve_plot(
2165
2165
  fit,
2166
- y: np.ndarray | pd.Series = None,
2167
- X: pd.DataFrame | np.ndarray = None,
2166
+ y: np.ndarray | pd.Series | None = None,
2167
+ X: pd.DataFrame | np.ndarray | None = None,
2168
2168
  title: str | None = None,
2169
2169
  width: int = config.height,
2170
2170
  height: int = config.height,
2171
2171
  linewidth: float = config.line_width,
2172
2172
  dpi: int = config.dpi,
2173
- save_path: str = None,
2174
- callback: any = None,
2175
- ax: Axes = None,
2173
+ save_path: str | None = None,
2174
+ callback: Callable | None = None,
2175
+ ax: Axes | None = None,
2176
2176
  ) -> None:
2177
2177
  """로지스틱 회귀 적합 결과의 ROC 곡선을 시각화한다.
2178
2178
 
@@ -2197,7 +2197,7 @@ def roc_curve_plot(
2197
2197
  """
2198
2198
  outparams = False
2199
2199
  if ax is None:
2200
- fig, ax = get_default_ax(width, height, 1, 1, dpi)
2200
+ fig, ax = get_default_ax(width, height, 1, 1, dpi) # type: ignore
2201
2201
  outparams = True
2202
2202
 
2203
2203
  # 실제값(y_true) 결정
@@ -2218,16 +2218,16 @@ def roc_curve_plot(
2218
2218
  roc_auc = auc(fpr, tpr)
2219
2219
 
2220
2220
  # ROC 곡선 그리기
2221
- ax.plot(fpr, tpr, color='darkorange', lw=linewidth, label=f'ROC curve (AUC = {roc_auc:.4f})')
2222
- ax.plot([0, 1], [0, 1], color='navy', lw=linewidth, linestyle='--', label='Random Classifier')
2221
+ ax.plot(fpr, tpr, color='darkorange', lw=linewidth, label=f'ROC curve (AUC = {roc_auc:.4f})') # type: ignore
2222
+ ax.plot([0, 1], [0, 1], color='navy', lw=linewidth, linestyle='--', label='Random Classifier') # type: ignore
2223
2223
 
2224
- ax.set_xlim([0.0, 1.0])
2225
- ax.set_ylim([0.0, 1.05])
2226
- ax.set_xlabel('위양성율 (False Positive Rate)', fontsize=8)
2227
- ax.set_ylabel('재현율 (True Positive Rate)', fontsize=8)
2228
- ax.set_title('ROC 곡선', fontsize=10, fontweight='bold')
2229
- ax.legend(loc="lower right", fontsize=7)
2230
- finalize_plot(ax, callback, outparams, save_path, True, title)
2224
+ ax.set_xlim([0.0, 1.0]) # type: ignore
2225
+ ax.set_ylim([0.0, 1.05]) # type: ignore
2226
+ ax.set_xlabel('위양성율 (False Positive Rate)', fontsize=8) # type: ignore
2227
+ ax.set_ylabel('재현율 (True Positive Rate)', fontsize=8) # type: ignore
2228
+ ax.set_title('ROC 곡선', fontsize=10, fontweight='bold') # type: ignore
2229
+ ax.legend(loc="lower right", fontsize=7) # type: ignore
2230
+ finalize_plot(ax, callback, outparams, save_path, True, title) # type: ignore
2231
2231
 
2232
2232
 
2233
2233
  # ===================================================================
@@ -2240,9 +2240,9 @@ def confusion_matrix_plot(
2240
2240
  width: int = config.width,
2241
2241
  height: int = config.height,
2242
2242
  dpi: int = config.dpi,
2243
- save_path: str = None,
2244
- callback: any = None,
2245
- ax: Axes = None,
2243
+ save_path: str | None = None,
2244
+ callback: Callable | None = None,
2245
+ ax: Axes | None = None,
2246
2246
  ) -> None:
2247
2247
  """로지스틱 회귀 적합 결과의 혼동행렬을 시각화한다.
2248
2248
 
@@ -2261,7 +2261,7 @@ def confusion_matrix_plot(
2261
2261
  """
2262
2262
  outparams = False
2263
2263
  if ax is None:
2264
- fig, ax = get_default_ax(width, height, 1, 1, dpi)
2264
+ fig, ax = get_default_ax(width, height, 1, 1, dpi) # type: ignore
2265
2265
  outparams = True
2266
2266
 
2267
2267
  # 학습 데이터 기반 실제값/예측 확률 결정
@@ -2277,9 +2277,9 @@ def confusion_matrix_plot(
2277
2277
  # 가독성을 위해 텍스트 크기/굵기 조정
2278
2278
  disp.plot(ax=ax, cmap='Blues', values_format='d', text_kw={"fontsize": 16, "weight": "bold"})
2279
2279
 
2280
- ax.set_title(f'혼동행렬 (임계값: {threshold})', fontsize=8, fontweight='bold')
2280
+ ax.set_title(f'혼동행렬 (임계값: {threshold})', fontsize=8, fontweight='bold') # type: ignore
2281
2281
 
2282
- finalize_plot(ax, callback, outparams, save_path, False, title)
2282
+ finalize_plot(ax, callback, outparams, save_path, False, title) # type: ignore
2283
2283
 
2284
2284
 
2285
2285
  # ===================================================================
@@ -2287,20 +2287,20 @@ def confusion_matrix_plot(
2287
2287
  # ===================================================================
2288
2288
  def radarplot(
2289
2289
  df: DataFrame,
2290
- columns: list = None,
2291
- hue: str = None,
2290
+ columns: list | None = None,
2291
+ hue: str | None = None,
2292
2292
  title: str | None = None,
2293
2293
  normalize: bool = True,
2294
2294
  fill: bool = True,
2295
2295
  fill_alpha: float = 0.25,
2296
- palette: str = None,
2296
+ palette: str | None = None,
2297
2297
  width: int = config.width,
2298
2298
  height: int = config.height,
2299
2299
  linewidth: float = config.line_width,
2300
2300
  dpi: int = config.dpi,
2301
- save_path: str = None,
2302
- callback: any = None,
2303
- ax: Axes = None,
2301
+ save_path: str | None = None,
2302
+ callback: Callable | None = None,
2303
+ ax: Axes | None = None,
2304
2304
  **params,
2305
2305
  ) -> None:
2306
2306
  """레이더 차트(방사형 차트)를 그린다.
@@ -2411,7 +2411,7 @@ def radarplot(
2411
2411
  else:
2412
2412
  ax.set_title('Radar Chart', pad=20)
2413
2413
 
2414
- finalize_plot(ax, callback, outparams, save_path, True, title)
2414
+ finalize_plot(ax, callback, outparams, save_path, True, title) # type: ignore
2415
2415
 
2416
2416
 
2417
2417
  # ===================================================================
@@ -2429,8 +2429,8 @@ def distribution_plot(
2429
2429
  height: int = config.height,
2430
2430
  linewidth: float = config.line_width,
2431
2431
  dpi: int = config.dpi,
2432
- save_path: str = None,
2433
- callback: any = None,
2432
+ save_path: str | None = None,
2433
+ callback: Callable | None = None,
2434
2434
  ) -> None:
2435
2435
  """연속형 데이터의 분포를 KDE와 Boxplot으로 시각화한다.
2436
2436
 
@@ -2477,7 +2477,7 @@ def distribution_plot(
2477
2477
  )
2478
2478
  else:
2479
2479
  boxplot(
2480
- df=data[column],
2480
+ df=data[column], # type: ignore
2481
2481
  linewidth=linewidth,
2482
2482
  ax=axes[1]
2483
2483
  )
@@ -2515,7 +2515,7 @@ def distribution_plot(
2515
2515
  )
2516
2516
  else:
2517
2517
  boxplot(
2518
- df=subset[column],
2518
+ df=subset[column], # type: ignore
2519
2519
  linewidth=linewidth,
2520
2520
  ax=right_ax
2521
2521
  )