목차

가상의 쇼핑몰을 분석 하기 위해 더미 데이터를 만들어 보았습니다. 랜덤 함수를 사용하기 때문에 실질적인 인사이트를 도출하기에는 어렵겠지만 국내 오픈마켓 매장 데이터를 구하기 어렵기 때문에 캐글에 공개되어 있는 해외 스토어 Olist Store의 데이터의 구조를 참고하여 필요한 컬럼만 만들었습니다.



0. 기초 설정 및 주 사용함수

프로젝트의 쇼핑몰 설정은 이렇습니다.

이름 내용
기간 2년(‘18~’19년도 주문내역)
회원 약 10만명 + (비회원 @)
지역 개수 25 (based on 서울시 구)
주문 50만건
상품 500가지
성비(남녀) 3:7
연령대
(10대: 20~30대:
40~50대: 60대 이상)
5:45:45:5
가구형태 1
(독신:2인이상)
35:65
가구형태 2
(미혼:기혼)
50:50
가구형태 3
(자녀 유:자녀 무)
7:3
쇼핑몰 내 등록된 제품 출시일 2015.01.01~


사용할 라이브러리

import numpy as np
import pandas as pd
from pandas import DataFrame
from pandas import Series
import random
from datetime import datetime
from datetime import timedelta

라이브러리를 다 불러와야 본문의 함수들을 사용할 수 있습니다.

주로 사용할 함수는 랜덤 생성 함수입니다.

#임의로 표본 추출
random.randint(low,  # 시작값
               high) # 끝값

np.random.randint(low,  # 시작값
                  high, # 끝값
                  size) # 표본 사이즈

#원소별 가중치 부여 후 추출
random.choices(population=range(1,5), # 표본
               weights=[1,2,3,4,5],   # 가중치
               k = n) # 추출 갯수



1. 고객 테이블(customer)

이름 형식
회원 0 ~ 99441
지역 개수 0 ~ 24
성별 남여 : 1/2
연령대 10대:1, 20~30대:2
40~50대:3, 60대 이상:4)
가구형태 1 독신여부 : 1/2
가구형태 2 결혼여부 : 1/2
가구형태 3 자녀여부 : 1/2

파일 불러오기 및 확인

#캐글 데이터 파일 불러오기
customer = pd.read_csv('olist_customers_dataset.csv', engine = 'python')
#컬럼 이름 확인
customer.columns  
#컬럼 이름 수정
customer.columns = ['customer_id', 'customer_unique_id', 'customer_zip_code_prefix', 'gu', 'customer_state']

더미 데이터 생성

#고객번호를 처음부터 끝까지 순서대로 부여
customer['customer_id'] = [i for i in range(len(customer))]

#지역 입력
gu_list=[1111000000,1114000000,1117000000,1120000000,1121500000,
         1123000000,1126000000,1129000000,1130500000,1132000000,
         1135000000,1138000000,1141000000,1144000000,1147000000,
         1150000000,1153000000,1154500000,1156000000,1159000000,
         1162000000,1165000000,1168000000,1171000000,1174000000]
customer['gu_code'] = random.choices(population=gu_list,
                                     k=len(customer))

#나이
customer['age'] = random.choices(population=[1,2,3,4],
                                 weights=[0.05,0.45,0.45,0.05],
                                 k=len(customer))

#성별 및 가구형태
customer['gender'] = random.choices(population=[1,2],
                                    weights=[3,7],
                                    k=len(customer))
customer['household'] = random.choices(population=[1,2],
                                    weights=[0.35,0.65],
                                    k=len(customer))
customer['marriage'] = random.choices(population=[1,2],
                                    k=len(customer))
customer['children'] = random.choices(population=[1,2],
                                    weights=[7,3],
                                    k=len(customer))

#csv 파일로 내보내기
customer.to_csv('customer_table.csv', encoding = 'utf-8-sig',
                index = False)



2. 상품 테이블(product)

이름 내용
상품 500가지
가격 2300 ~ 23000원
제품 출시일 2015.01.01 이후

#날짜 생성 사용자 함수
def random_dates(start, end, n=10):
    start_u = start.value//10**9
    end_u = end.value//10**9
    return pd.to_datetime(np.random.randint(start_u, end_u, n), unit='s')

#기간의 시작과 끝 지정
start = pd.to_datetime('2015-01-01')
end = pd.to_datetime('2019-12-31')

#테이블 생성
products = DataFrame(
                     {'product_id':[i for i in range(500)],
                      'product_release': random_dates(start, end, n=500),
                      'price':[f'{random.randrange(23,230)}00' for i in range(500)]
                     }
                    )

#csv 파일로 저장
products.to_csv('product.csv', index = False)



3. 주문 테이블(order)

이름 내용
주문건수 50만번
회원 약 10만명
기간 2년(‘18~’19년도 주문내역)

#상품 테이블에서 사용한 날짜 생성 사용자 함수 불러오기

#주문 기간 설정
start_2 = pd.to_datetime('2018-01-01')
end_2 = pd.to_datetime('2019-12-31')

#주문번호 및 고객번호 입력
orders = DataFrame({'order_id':[i for i in range(500000)],
                    'customer_id':[random.randrange(99441) for i in range(500000)]})

timestamp = Series(random_dates(start_2, end_2, 500000)).sort_values()
timestamp.index = [i for i in range(500000)]
orders['order_purchase_time_stamp'] = timestamp

#csv 파일로 저장
orders.to_csv('order.csv', index = False)



4. 주문한 상품 테이블(order_item)

이름 내용
주문건수 50만번
주문당 상품 수 1~8 (1개가 대부분)
상품 500가지
갯수 1~4 (1개가 대부분)

#주문건수와 주문당 상품 수 수정가능한 사용자 정의 함수
def order_n_num_2(ord_range, list_range):
    start = 0
    list = []
    for i in random.choices(range(list_range),
                            weights=[0.9 if i==0 else 0.05 for i in range(list_range)],
                            k=ord_range):
        ran_list = random.sample(range(500), i+1)
        for j in range(i+1):
            list.append([start,j+1, ran_list[j]])
        start += 1
    return list
    
fin_list = order_n_num_2(500000, 8)
data4 = DataFrame(fin_list)
data4.columns = ['order_id','order_items_id','product_id']

#수량은 임의대로 생성
data4['quantity'] = random.choices(population=range(1,5),weights=[8,1,1,1],k=len(data4))

#csv 파일로 저장
data4.to_csv('order_item.csv', index = False)



5. 전처리(preprocess)

제품 출시일보다 주문날짜가 앞이면 논리적으로 앞뒤가 맞지 않기 때문에 제품 출시일보다 주문날짜가 앞인경우 제품 출시일을 주문날짜 며칠 전으로 바꿔주는 과정입니다. 실제 데이터라면 결측치로 처리하거나 다른 방법을 알아보겠지만 직접 만드는 데이터기 때문에 수정을 하도록 하겠습니다.

#3개 csv 파일 불러오기
order = pd.read_csv('order.csv')
product = pd.read_csv('product.csv')
order_item = pd.read_csv('order_item.csv')

#LEFT JOIN 실행
order_mg = pd.merge(order, order_item, on = 'order_id')

#상품별 최초 주문일 가져오기
order_mg_2 = order_mg.groupby('product_id')['order_purchase_time_stamp'].min().reset_index()

#데이터 타입 확인
order_mg_2.dtypes
product.dtypes

#상품별 최초 주문일의 데이터 타입을 날짜 형식으로 변경
order_mg_2['order_purchase_time_stamp'] = order_mg_2['order_purchase_time_stamp'].apply(lambda _: datetime.strptime(_,"%Y-%m-%d %H:%M:%S"))
product['product_release'] = product['product_release'].apply(lambda _: datetime.strptime(_,"%Y-%m-%d"))

#본문 내용의 전처리
product['product_release'] = [product['product_release'][i]
 if product['product_release'][i] < order_mg_2['order_purchase_time_stamp'][i]
 else order_mg_2['order_purchase_time_stamp'][i] - timedelta(days = random.randrange(10)) for i in range(500)]

#csv 파일로 저장
product.to_csv('product_2.csv')