커뮤니티

K-means 클러스터링(K-means clustering)

프로필 이미지
dedoyes
2025-10-26 21:42:58
80
글번호 227318
답변완료

5일(기본입력값) 고가 돌파매수 저가 이탈매도 지표식을 AI(클러스터링) 방식으로 동적으로 선택하도록 설계한 예스트레이더용 구현 템플릿을 AI 질문했더니 아래처럼 제공했습니다만 예스랭귀지에 사용 부적합인지라 iM증권 예스트레이더에 부합하는 코드로 변환을 부탁드립니다.
// === 입력값 === input minN = 3 input maxN = 10 input stepN = 1 input perfMemory = 10 // 지수평활(미사용 시 단순평가) input fromCluster = "Best" // "Best" / "Average" / "Worst" input maxIter = 100 input maxBars = 1000 // 과거 평가용 봉 수 input defaultN = 5 // 안전 기본값 // === 후보 N 목록 생성 === var array<int> candN = array.new() for n = minN to maxN step stepN array.push(candN, n) endfor // === 각 후보의 퍼포먼스 계산 (단순 누적 수익) === var array<float> perfList = array.new() var array<int> factorList = array.new() // 현재 BAR_COUNT(플랫폼에 따라 이름 다를 수 있음) barsToEvaluate = min(barcount(), maxBars) // for each candidate N, 시뮬레이션 for idx = 0 to array.size(candN)-1 N = array.get(candN, idx) cash = 0.0 position = 0 // 0=flat, 1=long entry_price = 0.0 // 시간 흐름: 오래된 -> 최신 (플랫폼 루프 방법에 따라 조정) // 여기서는 i는 과거 offset (barsToEvaluate downto 1) for offset = barsToEvaluate down to 1 // 전봉 기준 N기간 최고/최저 (함수명: HHV / LLV 또는 highest/lowest 로 바꿔서 사용) hh = HHV(high, N, offset) // = offset번째 시점에서의 N기간 최고 (함수명 확인 필요) ll = LLV(low, N, offset) // 현재 바의 종가 (offset 시점) c = ref(close, offset) // 진입: 종가가 전봉 기준 N기간 최고 돌파 (전략 규칙) if position == 0 and c > hh position = 1 entry_price = c endif // 청산: 포지션 중 저가 이탈 if position == 1 and c < ll profit = c - entry_price cash = cash + profit position = 0 entry_price = 0.0 endif endfor // 시뮬레이션 종료 시 미청산 포지션 정리(평가 목적) if position == 1 last_close = close // 최신 종가 cash = cash + (last_close - entry_price) endif array.push(perfList, cash) array.push(factorList, N) endfor // === 퍼포먼스 값에서 초기 centroid 계산 (25/50/75 percentile) === // 플랫폼에 percentile 함수가 없다면 간단 정렬 후 인덱스로 대체 가능 perf_sorted = array.copy(perfList) array.sort(perf_sorted) // 오름차순 sizeP = array.size(perf_sorted) p25_idx = max(0, floor(0.25 * (sizeP - 1))) p50_idx = max(0, floor(0.50 * (sizeP - 1))) p75_idx = max(0, floor(0.75 * (sizeP - 1))) centroids = array.new() array.push(centroids, array.get(perf_sorted, p25_idx)) array.push(centroids, array.get(perf_sorted, p50_idx)) array.push(centroids, array.get(perf_sorted, p75_idx)) // === K-means 1D 반복 === for iter = 1 to maxIter // 초기화 clusters_perf = array.from(array.new(), array.new(), array.new()) clusters_factor = array.from(array.new(), array.new(), array.new()) // 할당 단계 for i = 0 to array.size(perfList)-1 val = array.get(perfList, i) // 거리 계산 d0 = abs(val - array.get(centroids, 0)) d1 = abs(val - array.get(centroids, 1)) d2 = abs(val - array.get(centroids, 2)) // 가장 작은 거리 인덱스 선택 idx_min = 0 if d1 < d0 idx_min = 1 if d2 < d1 idx_min = 2 endif else if d2 < d0 idx_min = 2 endif endif // 클러스터에 추가 array.push(array.get(clusters_perf, idx_min), val) array.push(array.get(clusters_factor, idx_min), array.get(factorList, i)) endfor // 중심 재계산 new_centroids = array.new() for k = 0 to 2 cperf = array.get(clusters_perf, k) if array.size(cperf) > 0 sumv = 0.0 for j = 0 to array.size(cperf)-1 sumv = sumv + array.get(cperf, j) endfor avgv = sumv / array.size(cperf) array.push(new_centroids, avgv) else // 빈 클러스터는 기존 centroid 유지 array.push(new_centroids, array.get(centroids, k)) endif endfor // 수렴 체크 (모두 같다면 종료) if array.get(new_centroids,0) == array.get(centroids,0) and array.get(new_centroids,1) == array.get(centroids,1) and array.get(new_centroids,2) == array.get(centroids,2) break endif centroids := new_centroids endfor // === 선택 클러스터 매핑 ('Worst'=0, 'Average'=1, 'Best'=2) === selIdx = 2 if fromCluster == "Worst" then selIdx = 0 endif if fromCluster == "Average" then selIdx = 1 endif // 선택 클러스터의 평균 N 계산 (없으면 기본값) chosenN = defaultN sel_factors = array.get(clusters_factor, selIdx) if array.size(sel_factors) > 0 ssum = 0 for i = 0 to array.size(sel_factors)-1 ssum = ssum + array.get(sel_factors, i) endfor chosenN = round(ssum / array.size(sel_factors)) endif // === 실시간 시그널: chosenN 사용 === // 최신 N기간 최고/최저 계산 (함수명 HHV/LLV 사용) curr_hh = HHV(high, chosenN) curr_ll = LLV(low, chosenN) buySignal = close > curr_hh sellSignal = close < curr_ll // 출력(화면 및 알림용) plot_int("ChosenN", chosenN) plot_bool("Buy", buySignal) plot_bool("Sell", sellSignal) // 실제 주문/포지션 관리는 전략 엔진 규칙에 맞춰 작성

지표
답변 1
프로필 이미지

예스스탁 예스스탁 답변

2025-10-27 17:06:23

안녕하세요. 예스스탁입니다. 올려주신 내용은 전반적인 내용 파악이 어려워 변환해 드리기 어렵습니다. 도움을 드리지 못해 죄송합니다. 즐거운 하루되세요