AI SCHOOL/TIL

[week 1] 공공 데이터 분석

moru_xz 2022. 12. 23. 17:36

첫 주 자습시간 공공데이터 분석 연습

 

주제 및 데이터 선정

1. 데이터

  • 통계 이름: 경찰청_범죄자 생활정도, 혼인관계 및 부모관계
  • 파일 이름: '경찰청_범죄자 생활정도, 혼인관계 및 부모관계_12_31_2020'
  • URL: https://www.data.go.kr/data/3074470/fileData.do
  • 데이터 설명: 전국 경찰관서에 고소, 고발, 인지 등으로 형사입건된 사건의 발생, 검거, 피의자에 대한 죄종별 분석 현황 (강도, 절도, 강간·강제추행) 생활정도(하류, 중류, 상류, 미상), 혼인관계(유배우자, 동거, 이혼, 사별), 미혼자부모관계 등에 따라 범죄자 분류

(매해 전년도 데이터 업로드, 하지만 아직 2022년에는 전년도 데이터가 공공데이터포털에 업로드 되지 않은 것으로 보임)

2. 주제 성정 이유

  • 최근 가장 많이 일어나는 범죄의 유형과 기타 다른 요소(생활정도, 결혼 유무 등)가 범죄에 연관 있는지에 대해 알아보기 위해
  • : 최근 빅데이터 범죄지도 시스템인 '지오프로스'를 알게 되었다. 범죄가 자주 일어나는 지역을 분석하여 범죄 예방 및 범죄자를 잡는데 활용하는 것이다. 이를 보고 최근 가장 자주 일어나는 범죄의 유형을 알아보고 생활정도와 결혼 유무 등 다른 요소가 범죄에 연관이 있는지에 대해 알아보고 범죄 예방 및 범죄자 검거에 도움이 되는 데이터를 얻고 싶어서 이러한 주제를 선택하였다.
In [ ]:
 
 
!sudo apt-get install -y fonts-nanum
!sudo fc-cache -fv
!rm ~/.cache/matplotlib -rf
'sudo'은(는) 내부 또는 외부 명령, 실행할 수 있는 프로그램, 또는
배치 파일이 아닙니다.
'sudo'은(는) 내부 또는 외부 명령, 실행할 수 있는 프로그램, 또는
배치 파일이 아닙니다.
In [1]:
 

 
import pandas as pd
import numpy as np
import matplotlib.pyplot as plt
import seaborn as sns
 
In [2]:
 

 
#폰트 설정
import matplotlib.pyplot as plt
plt.rc('font', family='NanumBarunGothic') # 폰트 설정
plt.rc('axes', unicode_minus=False) # 마이너스 폰트 설정
%config InlineBackend.figure_format='retina' # 그래프 글씨 뚜렷
 
In [3]:
 

 
# 한글 출력을 확인하기 위한 그래프
mon = ['mar','apr','may','jun','jul']
sales = [1,5,-7,3,7]
plt.rc('font', family='NanumGothic')
plt.title('월별 판매 실적')
plt.plot(mon, sales)
plt.show()
In [4]:
 

 
# 경고 메시지 무시
import warnings
warnings.filterwarnings('ignore')
warnings.simplefilter(action='ignore', category=FutureWarning)
 

데이터 불러오기

In [5]:
 

 
from google.colab import drive
drive.mount('/content/drive')
Drive already mounted at /content/drive; to attempt to forcibly remount, call drive.mount("/content/drive", force_remount=True).
In [6]:
 
 

 
drive_path = '/content/drive/MyDrive/문제해결을 위한 파이썬/과제/'
crime = pd.read_csv(drive_path + '경찰청_범죄자 생활정도, 혼인관계 및 부모관계_12_31_2020.csv', encoding = 'cp949')
 
In [7]:
 

 
crime.head()
Out[7]:
범죄대분류범죄중분류생활정도(계)생활정도(하류)생활정도(중류)생활정도(상류)생활정도(미상)혼인관계(계)혼인관계(소계)혼인관계(유배우자)...미혼자부모관계(실(양)부모)미혼자부모관계(계부모)미혼자부모관계(실부계모)미혼자부모관계(실부무모)미혼자부모관계(실모계부)미혼자부모관계(실모무부)미혼자부모관계(계부무모)미혼자부모관계(계모무부)미혼자부모관계(무부모)미상01234
강력범죄 살인기수 341 172 72 6 91 341 158 81 ... 45 0 2 8 0 17 0 0 20 91
강력범죄 살인미수등 454 276 93 3 82 454 234 123 ... 82 1 0 10 1 19 0 1 24 82
강력범죄 강도 1202 713 327 15 147 1202 257 144 ... 615 2 8 37 8 69 0 3 56 147
강력범죄 강간 6113 1831 1987 78 2217 6113 1295 798 ... 1998 8 23 143 19 270 0 2 139 2216
강력범죄 유사강간 934 331 362 7 234 934 236 145 ... 352 1 4 21 3 55 0 1 29 232

5 rows × 24 columns

In [8]:
 

 
crime.tail()
Out[8]:
범죄대분류범죄중분류생활정도(계)생활정도(하류)생활정도(중류)생활정도(상류)생활정도(미상)혼인관계(계)혼인관계(소계)혼인관계(유배우자)...미혼자부모관계(실(양)부모)미혼자부모관계(계부모)미혼자부모관계(실부계모)미혼자부모관계(실부무모)미혼자부모관계(실모계부)미혼자부모관계(실모무부)미혼자부모관계(계부무모)미혼자부모관계(계모무부)미혼자부모관계(무부모)미상3334353637
노동범죄 소계 613 264 209 7 133 613 369 275 ... 83 0 0 8 0 12 0 0 8 133
안보범죄 소계 678 338 260 3 77 678 156 101 ... 352 1 1 16 3 46 0 0 26 77
선거범죄 소계 1545 391 509 59 586 1545 720 618 ... 183 0 0 5 1 19 0 0 26 591
병역범죄 소계 3164 1955 911 11 287 3164 376 265 ... 1762 20 20 222 24 317 3 11 122 287
기타범죄 소계 244539 90514 74578 3118 76329 244539 110901 82079 ... 41152 272 227 2722 235 6961 35 80 5615 76339

5 rows × 24 columns

In [9]:
 

 
crime.info()
<class 'pandas.core.frame.DataFrame'>
RangeIndex: 38 entries, 0 to 37
Data columns (total 24 columns):
 #   Column           Non-Null Count  Dtype 
---  ------           --------------  ----- 
 0   범죄대분류            38 non-null     object
 1   범죄중분류            38 non-null     object
 2   생활정도(계)          38 non-null     int64 
 3   생활정도(하류)         38 non-null     int64 
 4   생활정도(중류)         38 non-null     int64 
 5   생활정도(상류)         38 non-null     int64 
 6   생활정도(미상)         38 non-null     int64 
 7   혼인관계(계)          38 non-null     int64 
 8   혼인관계(소계)         38 non-null     int64 
 9   혼인관계(유배우자)       38 non-null     int64 
 10  혼인관계(동거)         38 non-null     int64 
 11  혼인관계(이혼)         38 non-null     int64 
 12  혼인관계(사별)         38 non-null     int64 
 13  미혼자부모관계(소계)      38 non-null     int64 
 14  미혼자부모관계(실(양)부모)  38 non-null     int64 
 15  미혼자부모관계(계부모)     38 non-null     int64 
 16  미혼자부모관계(실부계모)    38 non-null     int64 
 17  미혼자부모관계(실부무모)    38 non-null     int64 
 18  미혼자부모관계(실모계부)    38 non-null     int64 
 19  미혼자부모관계(실모무부)    38 non-null     int64 
 20  미혼자부모관계(계부무모)    38 non-null     int64 
 21  미혼자부모관계(계모무부)    38 non-null     int64 
 22  미혼자부모관계(무부모)     38 non-null     int64 
 23  미상               38 non-null     int64 
dtypes: int64(22), object(2)
memory usage: 7.2+ KB
In [10]:
 

 
crime.isnull().sum() #NaN값 없는 것으로 확인
Out[10]:
범죄대분류              0
범죄중분류              0
생활정도(계)            0
생활정도(하류)           0
생활정도(중류)           0
생활정도(상류)           0
생활정도(미상)           0
혼인관계(계)            0
혼인관계(소계)           0
혼인관계(유배우자)         0
혼인관계(동거)           0
혼인관계(이혼)           0
혼인관계(사별)           0
미혼자부모관계(소계)        0
미혼자부모관계(실(양)부모)    0
미혼자부모관계(계부모)       0
미혼자부모관계(실부계모)      0
미혼자부모관계(실부무모)      0
미혼자부모관계(실모계부)      0
미혼자부모관계(실모무부)      0
미혼자부모관계(계부무모)      0
미혼자부모관계(계모무부)      0
미혼자부모관계(무부모)       0
미상                 0
dtype: int64
In [11]:
 

 
print(crime. index)
print(crime.columns)
RangeIndex(start=0, stop=38, step=1)
Index(['범죄대분류', '범죄중분류', '생활정도(계)', '생활정도(하류)', '생활정도(중류)', '생활정도(상류)',
       '생활정도(미상)', '혼인관계(계)', '혼인관계(소계)', '혼인관계(유배우자)', '혼인관계(동거)', '혼인관계(이혼)',
       '혼인관계(사별)', '미혼자부모관계(소계)', '미혼자부모관계(실(양)부모)', '미혼자부모관계(계부모)',
       '미혼자부모관계(실부계모)', '미혼자부모관계(실부무모)', '미혼자부모관계(실모계부)', '미혼자부모관계(실모무부)',
       '미혼자부모관계(계부무모)', '미혼자부모관계(계모무부)', '미혼자부모관계(무부모)', '미상'],
      dtype='object')
In [12]:
 

 
crime
Out[12]:
범죄대분류범죄중분류생활정도(계)생활정도(하류)생활정도(중류)생활정도(상류)생활정도(미상)혼인관계(계)혼인관계(소계)혼인관계(유배우자)...미혼자부모관계(실(양)부모)미혼자부모관계(계부모)미혼자부모관계(실부계모)미혼자부모관계(실부무모)미혼자부모관계(실모계부)미혼자부모관계(실모무부)미혼자부모관계(계부무모)미혼자부모관계(계모무부)미혼자부모관계(무부모)미상012345678910111213141516171819202122232425262728293031323334353637
강력범죄 살인기수 341 172 72 6 91 341 158 81 ... 45 0 2 8 0 17 0 0 20 91
강력범죄 살인미수등 454 276 93 3 82 454 234 123 ... 82 1 0 10 1 19 0 1 24 82
강력범죄 강도 1202 713 327 15 147 1202 257 144 ... 615 2 8 37 8 69 0 3 56 147
강력범죄 강간 6113 1831 1987 78 2217 6113 1295 798 ... 1998 8 23 143 19 270 0 2 139 2216
강력범죄 유사강간 934 331 362 7 234 934 236 145 ... 352 1 4 21 3 55 0 1 29 232
강력범죄 강제추행 16382 5805 6798 284 3495 16382 6527 4740 ... 4585 11 22 282 32 816 3 8 598 3498
강력범죄 기타 강간 강제추행등 349 157 126 5 61 349 99 53 ... 143 0 3 13 1 21 0 0 8 61
강력범죄 방화 1196 774 268 6 148 1196 579 312 ... 261 2 2 21 5 73 0 1 104 148
절도범죄 소계 98425 58626 28786 765 10248 98425 43426 27849 ... 31344 151 275 2486 244 4540 42 61 5600 10256
폭력범죄 상해 43552 23525 15251 455 4321 43552 24499 17317 ... 10254 54 63 620 64 1974 10 17 1674 4323
폭력범죄 폭행 178448 54911 41604 1232 80701 178448 62799 45974 ... 24738 165 121 1536 150 4247 19 36 3987 80650
폭력범죄 체포 감금 1695 550 391 34 720 1695 447 310 ... 416 2 1 17 1 51 0 0 38 722
폭력범죄 협박 22507 8965 6159 201 7182 22507 10326 7305 ... 3263 24 19 219 19 732 5 10 717 7173
폭력범죄 약취 유인 296 96 78 6 116 296 85 60 ... 74 0 0 4 0 8 0 0 9 116
폭력범죄 폭력행위등 25342 11325 8851 198 4968 25342 7198 5665 ... 11074 51 47 532 49 969 8 11 429 4974
폭력범죄 공갈 3434 1320 940 45 1129 3434 724 494 ... 1250 3 9 98 10 123 3 0 85 1129
폭력범죄 손괴 38716 18106 12731 476 7403 38716 19447 13596 ... 7948 47 48 547 50 1621 16 11 1574 7407
지능범죄 직무유기 947 9 64 2 872 947 62 61 ... 8 0 0 1 0 3 0 0 0 873
지능범죄 직권남용 1021 13 108 8 892 1021 108 98 ... 17 0 0 3 0 1 0 0 0 892
지능범죄 증수뢰 807 152 322 51 282 807 499 420 ... 17 0 0 0 0 2 0 0 7 282
지능범죄 통화 86 18 10 0 58 86 10 8 ... 12 0 0 1 0 2 0 0 3 58
지능범죄 문서 인장 15465 3457 3322 127 8559 15465 4201 3020 ... 2092 13 11 151 12 287 3 6 132 8557
지능범죄 유가증권인지 117 30 13 0 74 117 37 29 ... 6 0 0 0 0 0 0 0 0 74
지능범죄 사기 245009 88209 41033 1107 114660 245009 65125 43658 ... 46983 321 495 4139 469 7706 56 96 4935 114684
지능범죄 횡령 35930 13092 7670 240 14928 35930 13463 9531 ... 5126 38 42 386 31 919 6 6 990 14923
지능범죄 배임 8324 839 1291 129 6065 8324 1992 1634 ... 203 2 0 8 0 40 1 0 14 6064
풍속범죄 성풍속범죄 13546 5200 6283 173 1890 13546 2885 2130 ... 7137 24 31 335 37 778 5 7 416 1891
풍속범죄 도박범죄 21125 11280 7929 195 1721 21125 13358 9995 ... 4607 7 9 194 9 704 0 2 513 1722
특별경제범죄 소계 67904 29377 17586 621 20320 67904 30402 22194 ... 11531 105 49 778 61 2355 9 23 2277 20314
마약범죄 소계 11630 6628 3699 270 1033 11630 5643 3380 ... 3813 13 21 186 28 591 4 7 291 1033
보건범죄 소계 21810 9159 8139 734 3778 21810 12964 9429 ... 3835 44 16 206 17 568 2 5 375 3778
환경범죄 소계 4329 1726 1809 125 669 4329 3335 2707 ... 219 0 0 10 3 62 0 0 33 667
교통범죄 소계 356446 127215 92001 1725 135505 356446 140745 114965 ... 63086 301 199 3123 224 8383 46 178 4427 135734
노동범죄 소계 613 264 209 7 133 613 369 275 ... 83 0 0 8 0 12 0 0 8 133
안보범죄 소계 678 338 260 3 77 678 156 101 ... 352 1 1 16 3 46 0 0 26 77
선거범죄 소계 1545 391 509 59 586 1545 720 618 ... 183 0 0 5 1 19 0 0 26 591
병역범죄 소계 3164 1955 911 11 287 3164 376 265 ... 1762 20 20 222 24 317 3 11 122 287
기타범죄 소계 244539 90514 74578 3118 76329 244539 110901 82079 ... 41152 272 227 2722 235 6961 35 80 5615 76339

38 rows × 24 columns

분석 1: 범죄대분류 상위 5개 범죄

In [13]:
 

 
crime['범죄대분류'].unique()
Out[13]:
array(['강력범죄', '절도범죄', '폭력범죄', '지능범죄', '풍속범죄', '특별경제범죄', '마약범죄', '보건범죄',
       '환경범죄', '교통범죄', '노동범죄', '안보범죄', '선거범죄', '병역범죄', '기타범죄'],
      dtype=object)
In [14]:
 

 
df = crime.loc[:,['범죄대분류', '범죄중분류', '생활정도(계)']] 
#범죄대분류별 합계를 알아보기 위해 '생활정도(계)를 추출하여 새로운 df를 만듦
 
In [15]:
 

 
df = df.groupby(['범죄대분류']).sum()
 
In [16]:
 
 
df
Out[16]:
생활정도(계)범죄대분류강력범죄교통범죄기타범죄노동범죄마약범죄병역범죄보건범죄선거범죄안보범죄절도범죄지능범죄특별경제범죄폭력범죄풍속범죄환경범죄
26971
356446
244539
613
11630
3164
21810
1545
678
98425
307706
67904
313990
34671
4329
In [17]:
 

 
df = df.reset_index()
df= df.rename(columns={'생활정도(계)':'합'})
df.sort_values(by='합', ascending=False, inplace = True) 
df
Out[17]:
범죄대분류합11210291113064145783
교통범죄 356446
폭력범죄 313990
지능범죄 307706
기타범죄 244539
절도범죄 98425
특별경제범죄 67904
풍속범죄 34671
강력범죄 26971
보건범죄 21810
마약범죄 11630
환경범죄 4329
병역범죄 3164
선거범죄 1545
안보범죄 678
노동범죄 613
In [18]:
 

 
df_list = list(df['범죄대분류'])
 
In [19]:
 

 
plt.figure(figsize = (20, 5))
plt.title('범죄대분류 상위 5개 범죄', fontsize=20)
plt.rc('font', family='NanumBarunGothic')
sns.barplot(data=df, x= '범죄대분류', y = '합', order= df_list[:5])
plt.ylabel('총 빈도수', fontsize = 15)
plt.xlabel('범죄대분류', fontsize = 15)
plt.xticks(fontsize=13)
plt.yticks(fontsize=13)
plt.show()

분석 1 해석

  • 범죄대분류의 상위 5개 범죄를 확인한 결과 교통범죄, 폭력범죄, 지능범죄, 기타범죄, 절도범죄 순으로 범죄가 발생하고 있다.

분석 2: 범죄중분류 별 범죄 건수

In [20]:
 
 

 
crime['합계'] = crime['생활정도(하류)']+crime['생활정도(중류)']+crime['생활정도(상류)']+crime['생활정도(미상)']
# 범죄별 합계가 없어서 만듦
 
In [21]:
 
 

 
crime.iloc[8, 1] = '절도범죄'
crime.iloc[28, 1] = '특별경제범죄'
crime.iloc[29, 1] = '마약범죄'
crime.iloc[30, 1] = '보건범죄'
crime.iloc[31, 1] = '환경범죄'
crime.iloc[32, 1] = '교통범죄'
crime.iloc[33, 1] = '노동범죄'
crime.iloc[34, 1] = '안보범죄'
crime.iloc[35, 1] = '선거범죄'
crime.iloc[36, 1] = '병역범죄'
crime.iloc[37, 1] = '기타범죄'
#중분류 확인 위해 중분류 '소계'로 되어 있는 부분을 전부 범죄 대분류의 이름과 동일하게 만듦
 
In [22]:
 

 
crime['범죄중분류'].str.contains('소계').sum()
Out[22]:
0
In [23]:
 

 
plt.figure(figsize=(20,10))  
plt.xticks(rotation = 0)  
plt.rc('font', family='NanumBarunGothic')
plt.title('범죄중분류 별 범죄 건수', fontsize=20)
sns.barplot(
data = crime.sort_values(by='합계', ascending=False),
x = "합계",
y = "범죄중분류"
)
plt.show()

분석 2 해석

  • 범죄중분류 별 범죄 건수를 확인한 결과 교통범죄가 1위이다.
  • 교통범죄가 압도적으로 높고 그 뒤로는 사기와 기타범죄가 근소한 차이를 보이며 뒤따르고 있다.

분석 3: 폭력범죄의 범죄중분류 건수

범죄대분류 상위 5개 범죄 중 중분류로 나눠진 범죄인 교통범죄, 기타범죄, 절도범죄를 제외한 폭력범죄, 지능범죄의 중분류 건수를 알아본다.

In [24]:
 

 
a = (crime['범죄대분류'] == '폭력범죄')
df2 = crime.loc[a].drop(columns = '범죄대분류')
 
In [25]:
 

 
df3 = df2[['범죄중분류', '합계']].sort_values(by='합계', ascending = False)
df3
Out[25]:
범죄중분류합계109161412151113
폭행 178448
상해 43552
손괴 38716
폭력행위등 25342
협박 22507
공갈 3434
체포 감금 1695
약취 유인 296
In [26]:
 

 
plt.figure(figsize = (10,5))
plt.rc('font', family='NanumBarunGothic')
plt.title('폭력범죄의 범죄중분류 건수', fontsize = 18)
sns.barplot(data=df3, y='범죄중분류', x='합계')
sns.set_style('whitegrid') 
plt.xlabel('빈도수', fontsize = 13) 
plt.ylabel('범죄 종류', fontsize = 13) 
plt.xticks(fontsize = 15) 
plt.yticks(fontsize = 10, rotation = 12) 
plt.show()

분석 3 해석

  • 폭력범죄에서는 '폭행'의 빈도가 압도적으로 높은 것을 알 수 있다.
  • 그 다음으로는 상해, 손괴, 폭력행위 등의 순으로 범죄가 일어났다.

분석 4: 지능범죄의 범죄중분류 건수

In [27]:
 

 
b = (crime['범죄대분류'] == '지능범죄')
df4 = crime.loc[b].drop(columns = '범죄대분류')
df5 = df4[['범죄중분류', '합계']].sort_values(by='합계', ascending = False)
df5
Out[27]:
범죄중분류합계232421251817192220
사기 245009
횡령 35930
문서 인장 15465
배임 8324
직권남용 1021
직무유기 947
증수뢰 807
유가증권인지 117
통화 86
In [28]:
 

 
plt.figure(figsize = (10,5))
plt.rc('font', family='NanumBarunGothic')
plt.title('지능범죄의 범죄중분류 건수', fontsize = 18)
sns.barplot(data=df5, y='범죄중분류', x='합계')
sns.set_style('whitegrid') 
plt.xlabel('빈도수', fontsize = 13) 
plt.ylabel('범죄 종류', fontsize = 13) 
plt.xticks(fontsize = 15) 
plt.yticks(fontsize = 10, rotation = 12) 
plt.show()

분석 4 해석

  • 지능범죄에서는 '사기'의 빈도가 압도적으로 높은 것을 알 수 있다.
  • 지능범죄가 범죄대분류 별 상위 5개 범죄 중 3위를 차지하였지만 다양한 종류의 지능범죄를 행한 것이 아니라 대부분 '사기', '횡령'을 저지른 것을 알 수 있다.
 

김효정