2013. 9. 28. 04:55

'주옥같은사이트주저리' 카테고리의 다른 글

[링크]게임알고리즘 길찾기 등등  (0) 2013.11.04
흠..  (0) 2013.07.27
[Link]ETRI 전자저널  (0) 2012.04.26
[LINK]IOS_Stuff  (0) 2012.04.25
[Link]Reverse Engineering Max OS X  (0) 2012.04.25
Posted by 땡보
2013. 9. 23. 10:57

#AutoIt3Wrapper_icon=AutoㅇㅇㅇㅇLecture.ico


; 목적 : AutoIt 학습 및 imagesearch 라이브러리 사용법 학습

; 버전 : 3.3.8.1

; 일자 : 2013.06월의 어느날

; 동작 :

; ㅇㅇㅇㅇ 사내 산업안전교육 온라인 교육 및 시험을 자동으로 수강 및 응시한다.


#include <ImageSearch.au3>


Global $gs_mainwintitle = "ㅇㅇㅇㅇ㈜"

Global $gs_lecwintitle = "교안보기..."

Global $gs_googledef = "Google 계정"

Global $gs_chromedef = "- Chrome"

Global $ghWnd_MWin = 0

Global $gs_userid = ""

Global $gs_userpw = ""

Global $gl_maxleccnt = 5

Global $gl_limitsec = 1210

Global $gpos_basex1 = 0

Global $gpos_basey1 = 0

Global $Paused

Global $gl_tolerance = 0


If MutexExists("ㅇㅇㅇㅇOnlineLecture") Then

MsgBox(0, "알림", "자동수강이 이미 실행 중입니다.")

ToolTip("")

Exit

EndIf


Func MutexExists($sOccurenceName)

Local $ERROR_ALREADY_EXISTS = 183, $handle, $lastError

$sOccurenceName = StringReplace($sOccurenceName, "", "")

$handle = DllCall("kernel32.dll", "int", "CreateMutex", "int", 0, "long", 1, "str", $sOccurenceName)

$lastError = DllCall("kernel32.dll", "int", "GetLastError")

Return $lastError[0] = $ERROR_ALREADY_EXISTS

EndFunc


HotKeySet("{ESC}", "ExitForce")

HotKeySet("+!p", "TogglePause")


ToolTip("산업안전 자동수강 실행중...", 0, 0)


If FileExists(@ProgramFilesDir & "\Google\Chrome\Application\chrome.exe") Then

If MsgBox(4,"알림", "ㅇㅇㅇㅇ 온라인 법정안전교육 자동수강을 시작하시겠습니까?" & @CRLF & _

                        "(모든 강의를 수강하신 후 이 프로그램을 재실행 하시면" & @CRLF & " 자동 시험응시가 가능합니다!!)") == 6 Then


While 1

$gl_tolerance = InputBox("입력", "이미지 검색 오차범위를 설정하여 주세요.(1~10사이숫자범위)" & @CRLF & @CRLF & "검색 오차범위는 프로그램이 창을 찾지 못하면 높게 잡아주세요!!" & @CRLF & @CRLF &"오차범위가 낮을수록 프로그램 정확도가 올라갑니다!!" & @CRLF & "(3정도가 가장 좋은 인식율을 보이는것 같습니다)",3,"",400,250)

If $gl_tolerance == "" Then

If MsgBox(4, "입력", "프로그램을 실행을 중지하시겠습니까?") == 6 Then

ToolTip("")

Exit

EndIf

EndIf


If $gl_tolerance < 1 or  $gl_tolerance > 10 Then

MsgBox(0, "알림", "1~10 사이 숫자만 입력가능합니다!!")

Else

ExitLoop

EndIf

WEnd

Main()

Else

MsgBox(0, "알림", "사용자 요청으로 자동수강을 종료합니다!!", 3)

ToolTip("")

Exit

EndIf

Else

If MsgBox(4, "알림", "크롬 브라우저가 설지되어 있지 않습니다!!" & @CRLF & "자동수강은 크롬 브라우저가 설치되어 있어야 정상 동작합니다!!" & @CRLF & "크롬 브라우저를 설치하시겠습니까?") == 6 Then

$ll_retval = ShellExecute("explorer.exe", "http://www.google.com/intl/ko/chrome/browser/")

If $ll_retval == 1 Then

MsgBox(0, "알림", "멋진 선택이십니다. 크롬 설치후 다시한번 실행하여 주세요!!")

ToolTip("")

Exit

Else

MsgBox(0, "알림", "알수없는 오류로 인하여 크롬브라우저 설치 진행에 실패하였습니다!! 아쉽지만 다음기회에....")

ToolTip("")

Exit

EndIf

Else

MsgBox(0, "알림", "크롬브라우저가 없어 진행을 종료합니다!!")

ToolTip("")

Exit

EndIf

EndIf


Func Main()


$lpos_x1 = 0

$lpos_y1 = 0


$ll_retval = 0


    While ProcessExists("chrome.exe")

        ProcessClose("chrome.exe")

    WEnd


Close_ExistWindow($gs_mainwintitle)

Close_ExistWindow($gs_lecwintitle)


$ghWnd_MWin = Find_Window($gs_mainwintitle)


If $ghWnd_MWin < 0 Then

MsgBox(0, "알림", "ㅇㅇㅇㅇ 온라인 법정안전교육 창을 찾지 못했습니다!!")

ToolTip("")

Exit

EndIf


$ll_retval = WinMove($ghWnd_MWin,"", 0,0,1024,768)


If $ll_retval == 0 Then

MsgBox(0, "알림", "ㅇㅇㅇㅇ 온라인 법정안전교육 창을 찾지 못했습니다!!")

ToolTip("")

Exit

EndIf


Activate_MainWin($ghWnd_MWin)

$ll_retval = _WaitForImageSearch("GoogleDef.bmp",3,1,$lpos_x1,$lpos_y1,$gl_tolerance)

If $ll_retval == 1 Then

Activate_MainWin($ghWnd_MWin)

MouseMove($lpos_x1+85,$lpos_y1)

Sleep(100)

MouseClick("left")

EndIf


Activate_MainWin($ghWnd_MWin)

$ll_retval = _WaitForImageSearch("ChromeDef.bmp",3,1,$lpos_x1,$lpos_y1,$gl_tolerance)

If $ll_retval == 1 Then

Activate_MainWin($ghWnd_MWin)

MouseMove($lpos_x1,$lpos_y1)

Sleep(100)

MouseClick("left")

EndIf


Activate_MainWin($ghWnd_MWin)

$ll_retval = _WaitForImageSearch("LectureDef.bmp",3,1,$lpos_x1,$lpos_y1,$gl_tolerance)

If $ll_retval == 1 Then

Activate_MainWin($ghWnd_MWin)

MouseMove($lpos_x1,$lpos_y1)

Sleep(100)

MouseClick("left")

EndIf


Activate_MainWin($ghWnd_MWin)


Input_UserInfo()


Login_Site()


GoToLectureRoom()


WatchLecture()


EndFunc


Func GetBasePosition()

$lpos_x1 = 0

$lpos_y1 = 0

$lpos = 0


Activate_MainWin($ghWnd_MWin)

$ll_retval =  _WaitForImageSearch("BasePosition.bmp",5,1,$lpos_x1,$lpos_y1,$gl_tolerance)

If $ll_retval <> 1 Then

MsgBox(0,"알림", "시험답안지 기준점을 찾는데 실패하였습니다" & @CRLF & "프로그램을 종료합니다!!")

ToolTip("")

Exit

EndIf

MouseMove($lpos_x1, $lpos_y1)

$lpos = MouseGetPos()

$gpos_basex1 = $lpos[0] + 1

$gpos_basey1 = $lpos[1] + 3

;MsgBox(0, "알림", "Mouse x,y:" & $pos[0] & "," & $pos[1])

EndFunc


Func AnswerSheetMatrix($al_ques_no, $al_answ_no, ByRef $apos_x1, ByRef $apos_y1)

$lpos_x1 = $gpos_basex1

If $al_ques_no <= 6 Then

$lpos_y1 = $gpos_basey1

Else

$al_ques_no = $al_ques_no - 7

$lpos_y1 = $gpos_basey1 + 316

EndIf


$apos_x1 = $lpos_x1 + (41 * $al_answ_no)

$apos_y1 = $lpos_y1 + (57 * $al_ques_no)

EndFunc


Func EnterExam()

Dim $larray_answer[11] = [0,4,4,4,2,1,4,2,3,4,3]


$lpos_x1 = 0

$lpos_y1 = 0

Activate_MainWin($ghWnd_MWin)

$ll_retval =  _WaitForImageSearch("ExamSeason.bmp",5,1,$lpos_x1,$lpos_y1,$gl_tolerance)

If $ll_retval <> 1 Then

MsgBox(0,"알림", "3분기 근로자 정기교육만 자동응시 가능합니다!!" & @CRLF & "프로그램을 종료합니다!!")

ToolTip("")

Exit

EndIf

Activate_MainWin($ghWnd_MWin)

$ll_retval =  _WaitForImageSearch("EnterExam01.bmp",5,1,$lpos_x1,$lpos_y1,$gl_tolerance)

If $ll_retval <> 1 Then

Activate_MainWin($ghWnd_MWin)

$ll_retval =  _WaitForImageSearch("EnterExam02.bmp",5,1,$lpos_x1,$lpos_y1,$gl_tolerance)

EndIf


If $ll_retval <> 1 Then

MsgBox(0,"알림", "응시할 시험이 없습니다!!" & @CRLF & "프로그램을 종료합니다!!")

ToolTip("")

Exit

EndIf


Activate_MainWin($ghWnd_MWin)

MouseMove($lpos_x1,$lpos_y1)

Sleep(1000)

MouseClick("left")

Sleep(1000)

MouseMove(0,0)


For $i = 1 To 6

Send("{RIGHT}")

Sleep(50)

Next


Activate_MainWin($ghWnd_MWin)

$ll_retval =  _WaitForImageSearch("AnswerSheet.bmp",5,1,$lpos_x1,$lpos_y1,$gl_tolerance)


If $ll_retval <> 1 Then

MsgBox(0,"알림", "답안지를 찾을 수 없습니다!!" & @CRLF & "프로그램을 종료합니다!!")

ToolTip("")

Exit

EndIf


GetBasePosition()


Activate_MainWin($ghWnd_MWin)

MouseMove($lpos_x1,$lpos_y1)

Sleep(100)

MouseClick("left")

$lpos_basex1 = $lpos_x1

$lpos_basey1 = $lpos_y1


For $i = 1 To UBound($larray_answer) - 1

If $i == 8 Then

Activate_MainWin($ghWnd_MWin)

MouseMove($lpos_basex1,$lpos_basey1)

Sleep(50)

MouseClick("left")

For $j = 1 To 3

Activate_MainWin($ghWnd_MWin)

Send("{DOWN}")

Sleep(50)

Next

EndIf


AnswerSheetMatrix($i - 1, $larray_answer[$i] - 1, $lpos_x1, $lpos_y1)

Activate_MainWin($ghWnd_MWin)

MouseMove($lpos_x1,$lpos_y1)

Sleep(100)

MouseClick("left")

Sleep(100)

Next


Activate_MainWin($ghWnd_MWin)

MouseMove($lpos_basex1,$lpos_basey1)

Sleep(50)

MouseClick("left")

For $j = 1 To 3

Activate_MainWin($ghWnd_MWin)

Send("{DOWN}")

Sleep(50)

Next


Activate_MainWin($ghWnd_MWin)

$ll_retval =  _WaitForImageSearch("Submit.bmp",5,1,$lpos_x1,$lpos_y1,$gl_tolerance)

If $ll_retval <> 1 Then

MsgBox(0,"알림", "제출버튼을 찾을 수 없습니다!!" & @CRLF & "수동으로 제출해주세요!!")

EndIf


Activate_MainWin($ghWnd_MWin)

MouseMove($lpos_x1,$lpos_y1)

Sleep(100)

MouseClick("left")


Activate_MainWin($ghWnd_MWin)

$ll_retval =  _WaitForImageSearch("Confirm.bmp",5,1,$lpos_x1,$lpos_y1,$gl_tolerance)

If $ll_retval <> 1 Then

MsgBox(0,"알림", "제출버튼을 찾을 수 없습니다!!" & @CRLF & "수동으로 제출해주세요!!")

EndIf


Activate_MainWin($ghWnd_MWin)

MouseMove($lpos_x1,$lpos_y1)

Sleep(100)

MouseClick("left")


MsgBox(0, "알림", "시험 응시가 끝났습니다!! 쌍콤한 하루 되세요~")

ToolTip("")

Exit

EndFunc


Func WatchLecture()

$lpos_x1 = 0

$lpos_y1 = 0

$ll_errcnt = 0


$idx_lec = 1

While 1

Activate_MainWin($ghWnd_MWin)

$ll_retval =  _WaitForImageSearch("Completing.bmp",5,1,$lpos_x1,$lpos_y1,$gl_tolerance)

If $ll_retval <> 1 Then

Activate_MainWin($ghWnd_MWin)

$ll_retval =  _WaitForImageSearch("NotComplete.bmp",5,1,$lpos_x1,$lpos_y1,$gl_tolerance)

EndIf

If $ll_retval == 1 Then

$lpos_x1 = $lpos_x1 - 330

Activate_MainWin($ghWnd_MWin)

MouseMove($lpos_x1,$lpos_y1)

Sleep(1000)

MouseClick("left")

Sleep(2000)

MouseMove(0,0)

$ll_retval = WinSetState($ghWnd_MWin, "", @SW_MINIMIZE)

$ll_retval = WinExists($gs_lecwintitle)

If $ll_retval == 1 Then

$lhWnd_LecWin = WinGetHandle($gs_lecwintitle)

$ll_retval = WinMove($lhWnd_LecWin,"", 0,0,1024,768)

$ll_retval = WinSetState($lhWnd_LecWin, "", @SW_MINIMIZE)


$ls_msg = ""


ProgressOn("자동수강 진행사항", String($idx_lec) & "차시 강의 " & "0% 수강중...(다른작업 가능합니다.)", "")


$ll_watchrate = 0


; 테스트 30초 수강!!

;$gl_limitsec = 10

For $ll_remainsec = 1 To $gl_limitsec

$ll_watchrate = Round(($ll_remainsec / $gl_limitsec) * 100, 0)

$ls_msg = "중지:ESC / 일시정지:Alt+Shift+p"

$ll_retval = WinExists($lhWnd_LecWin)

If $ll_retval <> 1 Then

ProgressOff()

MsgBox(0, "알림", "강의창이 사라져 자동수강을 종료합니다!!")

ToolTip("")

Exit

EndIf

ProgressSet($ll_watchrate, String($ll_watchrate) & "% 수강중...(다른작업 가능합니다.)", $ls_msg)

Sleep(1000)

Next


ProgressSet(100, "강의 100% 수강완료!!", $ls_msg)

Sleep(500)

ProgressOff()


WinClose($lhWnd_LecWin)


$idx_lec = $idx_lec + 1


If $idx_lec > $gl_maxleccnt Then

ExitLoop

EndIf

Else

MsgBox(0,"알림","미수강 강의 리스트를 찾지 못하였습니다!!" & @CRLF & "3초후 강의를 재탐색 합니다!!", 3)

WinClose($gs_lecwintitle)

$ll_errcnt = $ll_errcnt + 1

If $ll_errcnt >= 3 Then

MsgBox(0, "알림", "더이상 수강 가능한 강의를 찾을 수 없어 프로그램을 종료 합니다!!")

ToolTip("")

Exit

EndIf

EndIf

Else

MsgBox(0,"알림","미수강 강의 리스트를 찾지 못하였습니다!!" & @CRLF & "3초후 강의를 재탐색 합니다!!", 3)

WinClose($gs_lecwintitle)

$ll_errcnt = $ll_errcnt + 1

If $ll_errcnt >= 3 Then

MsgBox(0, "알림", "더이상 수강 가능한 강의를 찾을 수 없어 프로그램을 종료 합니다!!")

ToolTip("")

Exit

EndIf

EndIf

WEnd

EndFunc


Func GoToLectureRoom()

$lpos_x1 = 0

$lpos_y1 = 0


Activate_MainWin($ghWnd_MWin)

For $i = 1 To 3


If $i == 3 Then

Activate_MainWin($ghWnd_MWin)

$ll_retval =  _WaitForImageSearch("PossibleExam01.bmp",5,1,$lpos_x1,$lpos_y1,$gl_tolerance)

If $ll_retval == 1 Then

If MsgBox(4, "알림", "이미 모든 강의를 수강하셨습니다!! 시험에 응시 하시겠습니까?") == 6 Then

EnterExam()

ToolTip("")

Exit

EndIf

EndIf

EndIf


Activate_MainWin($ghWnd_MWin)

$ll_retval =  _WaitForImageSearch("ClassRoom0" & String($i) & ".bmp",5,1,$lpos_x1,$lpos_y1,$gl_tolerance)

If $ll_retval == 1 Then

Activate_MainWin($ghWnd_MWin)

MouseMove($lpos_x1,$lpos_y1)

Sleep(1000)

MouseClick("left")

Sleep(1000)

Else

MsgBox(0,"알림","강의실 바로가기를 찾지 못하였습니다!!")

ToolTip("")

Exit

EndIf

Next

EndFunc


Func Activate_MainWin($ahWnd_Win)

$ll_retval = WinActivate($ahWnd_Win)

MouseMove(0,0)

If $ll_retval == 0 Then

MsgBox(0, "알림", "ㅇㅇㅇㅇ 온라인 법정안전교육 창을 찾지 못했습니다!!")

ToolTip("")

Exit

EndIf

EndFunc


Func Login_Site()

$lpos_x1 = 0

$lpos_y1 = 0


Activate_MainWin($ghWnd_MWin)


$ll_retval = _WaitForImageSearch("Logout.bmp",5,1,$lpos_x1,$lpos_y1,$gl_tolerance)

if $ll_retval == 1 Then

MouseMove($lpos_x1-55,$lpos_y1+19)

Sleep(1000)

MouseClick("left")

Sleep(3000)

EndIf


$lpos_x1 = 0

$lpos_y1 = 0


$ll_retval = _WaitForImageSearch("Login.bmp",5,1,$lpos_x1,$lpos_y1,$gl_tolerance)

If $ll_retval == 1 Then

Activate_MainWin($ghWnd_MWin)

MouseMove($lpos_x1,$lpos_y1-12,1)

MouseClick("left")

Send($gs_userid)

Sleep(500)

Send("{Enter}")

Sleep(500)

Send("{Tab}")

Sleep(500)

Send($gs_userpw)

Send("{Enter}")

$ll_retval = _WaitForImageSearch("Loginfail.bmp",5,1,$lpos_x1,$lpos_y1,$gl_tolerance)

If $ll_retval == 1 Then

Close_ExistWindow($gs_mainwintitle)

MsgBox(0, "알림", "입력하신 ID 또는 PW가 올바르지 않습니다!!" & @CRLF & "확인 후 다시 시도하여 주세요!!")

ToolTip("")

Exit

EndIf

Else

MsgBox(0,"알림","로그인창을 찾지 못하였습니다!!")

ToolTip("")

Exit

EndIf

EndFunc


Func Input_UserInfo()

$gs_userid = ""

$gs_userpw = ""


$gs_userid = InputBox("입력", "교육대상자 ID를 입력!!" & @CRLF & "(그룹웨어ID[사번아님]})")

$gs_userpw = InputBox("입력", "교육대상자 비밀번호 입력!!" & @CRLF & "(기본패스워드 1111)", "", "*")


If $gs_userid == "" Or $gs_userpw == "" Then

If MsgBox(4, "알림", "교육대상자 ID 또는 패스워드가 올바르지 않습니다!!" & @CRLF & "다시 입력하시겠습니까?") == 6 Then

Input_UserInfo()

Else

MsgBox(0, "알림", "프로그램을 종료합니다!!",5)

ToolTip("")

Exit

EndIf

Else

Return 1

EndIf

EndFunc


Func Find_Window($as_wintitle)

$ll_retval = 0


$ll_retval = WinExists($as_wintitle)


If $ll_retval == 1 Then

Return WinGetHandle($as_wintitle)

Else

$ll_retval = ShellExecute("chrome.exe", "--incognito http://ㅇㅇㅇㅇ.산업안전보건교육.kr/")

If $ll_retval == 1 Then

Sleep(2000)

Return WinGetHandle($as_wintitle)

Else

Return -1

EndIf

EndIf

EndFunc


Func Close_ExistWindow($as_wintitle)


While 1

$lhWnd_temp = 0

$ll_retval = 0

$lpos_x1 = 0

$lpos_y1 = 0


$ll_retval = WinExists($as_wintitle)


If $ll_retval == 1 Then

$lhWnd_temp = WinGetHandle($as_wintitle)

Activate_MainWin($lhWnd_temp)

Sleep(500)


$ll_retval = WinMove($lhWnd_temp,"", 0,0,1024,768)

If $ll_retval == 0 Then

MsgBox(0, "알림", "ㅇㅇㅇㅇ 온라인 법정안전교육 창을 찾지 못했습니다!!")

ToolTip("")

Exit

EndIf

$ll_retval = _WaitForImageSearch("Logout.bmp",5,1,$lpos_x1,$lpos_y1,$gl_tolerance)

if $ll_retval == 1 Then

MouseMove($lpos_x1-55,$lpos_y1+19)

Sleep(500)

MouseClick("left")

Sleep(1000)

EndIf

WinClose($lhWnd_temp)

Else

ExitLoop

EndIf

WEnd


EndFunc


Func ExitForce()

If MsgBox(4,"알림", "ㅇㅇㅇㅇ 온라인 법정안전교육 자동수강을 강제 종료 하시겠습니까?") == 6 Then

ToolTip("")

Exit

EndIf

EndFunc


Func TogglePause()

    $Paused = Not $Paused

    While $Paused

        Sleep(100)

        ToolTip("자동수강 일시정지중...", -1, -1)

    WEnd

    ToolTip("자동수강 진행중....", -1, -1)

EndFunc


'Study > AutoIt/AutoHotKey' 카테고리의 다른 글

[펌]Alternative to _StringEncrypt()  (0) 2013.07.29
Posted by 땡보
2013. 9. 23. 06:42

'Study > python' 카테고리의 다른 글

[연습]wxpython rss reader  (0) 2013.10.06
wxpython webview test  (0) 2013.10.05
[연습]손바닥삼국지 오토  (0) 2013.09.22
[연습]Python regular expression & sqlite  (0) 2013.09.22
[펌]Unicode In Python, Completely Demystified  (0) 2013.09.18
Posted by 땡보
2013. 9. 22. 15:53

본 소스 코드는 개인 학습용으로 연습삼아 작성한 코드 입니다.

또한 2012년 작성 코드로 현재 동작 여부는 알 수 없습니다.

혹시나 퍼가셔서 사용하시거나, 또는 수정하여 사용하시다 발생하는 모든 책임은 사용자 본인에게 있음을 알려드립니다.

#!/usr/bin/env python

#-*- coding:ms949 -*-


'''

    목  적 : Python 정규식 및 urllib 연습

    버  전 : Python 3.2

    연습일 : 2012.04.16

    동  작 :

    모바일 게임 어플인 '손바닥삼국지'를 자동으로 플레이 해준다.

'''

import time

import http.client

import urllib.parse

import re

import random

import sys

import os

import copy


base_user_id   = ''

base_user_pw   = ''

base_user_host = 'k5.tapsg.com'

base_cookie    = ''

base_token     = ''

base_city_id   = ''

city_id_all    = ''

base_max_cnt   = 500                    #오랑캐 최대 검색 좌표수(섭 트레픽 증가로 인한 계정 블럭을 방지)

base_find_cnt  = 100

base_find_type = 3                      #찾고 싶은 오랑캐 타입(별!!! 카운트 내림차수 정렬임!!)


def chk_auth():

    get_auth_url =  '/auth.html'

    html_source = get_html_response(get_auth_url, 3)

    if html_source == '::ERROR::':

        sys.exit()

    if '"code":0' in html_source:

        #print('실행 장소 인증 성공')

        return

    else:

        print('허가되지 않은 장소에서의실행 요청입니다!!')

        sys.exit()


def auto_attack(city_id, inteval_sec, type_orang, type_soldier, num_soldier):

    next_ip             = 'next'

    err_cnt             = 0

    food_per_attack     = 0

    interval_per_attack = 0

    city_tot_money      = 0

    city_tot_food       = 0

    need_chg_tot_gold   = 0


    while True:

        # 도시정보 호출 후 식량자원량 추출

        city_resource = get_city_resource(city_id)

        if city_resource:

            if city_resource == '::ERROR::':

                if err_cnt <= 3:

                    err_cnt += 1

                    print('[01]Error발생')

                    timesleep(5)

                    continue

                else:

                    print('3회 이상 에러가 발생하여 자동 사냥을 중단합니다!!')

                    return -1

            else:

                city_tot_money = city_resource[0][0]

                city_tot_food  = city_resource[0][1]

                next_ip = 'next'

                rand_timesleep()                

        else:

            if err_cnt <= 3:

                err_cnt += 1

                print('[02]Error발생')

                timesleep(5)

                continue

            else:

                print('3회 이상 에러가 발생하여 자동 사냥을 중단합니다!!')

                return -1

        

        if next_ip == 'next':

            # 1. 목록(의미없음)

            # GET /game/api_fav.php?jsonpcallback=jsonp1334359483814&_=1334372334923&key=ac91d18916be985c476e6a4bbfb7bd56&_l=kr&_p=SG-IPHONE-KR HTTP/1.1

            # jsonp1334423944539({"code":0,"ret":{"friend":[{"id":6800,"nick":"harddisk","nationid":2,"level":57,"guild":"\uace0\ud55c\uc74d","guildid":13,"gpower":5,"gflag":64,"protection":0,"status":0,"conq":[0,0,null]},{"id":19762,"nick":"shoowhip","nationid":2,"level":37,"guild":"\uace0\ud55c\uc74d","guildid":13,"gpower":5,"gflag":64,"protection":0,"status":0,"conq":[0,0,null]},{"id":19788,"nick":"\uac81\ud608\uc774","nationid":1,"level":50,"guild":"\uace0\ud55c\uc74d","guildid":13,"gpower":5,"gflag":64,"protection":0,"status":0,"conq":[0,0,null]},{"id":19794,"nick":"chakani710","nationid":3,"level":47,"guild":"\uace0\ud55c\uc74d","guildid":13,"gpower":5,"gflag":64,"protection":0,"status":0,"conq":[0,0,null]},{"id":20424,"nick":"sphere604","nationid":1,"level":47,"guild":"\uace0\ud55c\uc74d","guildid":13,"gpower":5,"gflag":64,"protection":0,"status":0,"conq":[0,0,null]},{"id":20834,"nick":"\uad00\uc6b0\uc6b4\uc7a5","nationid":1,"level":20,"guild":"\uc2ed\uc790\uad70","guildid":58,"gpower":5,"gflag":68,"protection":0,"status":0,"conq":[0,0,null]},{"id":21006,"nick":"abcd1004","nationid":1,"level":12,"guild":"","guildid":0,"gpower":0,"gflag":1,"protection":0,"status":0,"conq":[0,0,null]},{"id":21045,"nick":"\uac00\ub294\ube44\uc628\ub2e4","nationid":2,"level":34,"guild":"","guildid":0,"gpower":0,"gflag":1,"protection":0,"status":0,"conq":[0,0,null]},{"id":21080,"nick":"\uc815\uc624","nationid":1,"level":25,"guild":"\uace0\ud55c\uc74d","guildid":13,"gpower":5,"gflag":64,"protection":0,"status":0,"conq":[0,0,null]}]}})

            get_list_url = '/game/api_fav.php?jsonpcallback=jsonp' + get_time() + '&_=' + get_time() + '&key=' + base_token + '&_l=kr&_p=SG-IPHONE-KR{}HTTP/1.1'.format(urllib.parse.quote(' '))

            html_source = get_html_response(get_list_url, 2)

            if html_source == '::ERROR::':

                if err_cnt <= 3:

                    err_cnt += 1

                    print('[03]Error발생')

                    timesleep(5)

                    continue

                else:

                    print('3회 이상 에러가 발생하여 자동 사냥을 중단합니다!!')

                    return -1

            # 에러만 아니면 성공여부 상관없음!!

            next_ip = 'next'

            rand_timesleep()


        if next_ip == 'next':

            # 2. 친추 오랑캐 리스트 (좌표, 공격 횟수, 별수 추출) 

            # GET /game/api_fav.php?jsonpcallback=jsonp1334359483815&_=1334372336989&key=ac91d18916be985c476e6a4bbfb7bd56&act=getfavnpc&cat=2&_l=kr&_p=SG-IPHONE-KR HTTP/1.1

            # jsonp1334423982684({"code":0,"ret":{"favs":[[182038,258,27,1,0],[182039,253,26,1,0],[182040,239,19,1,0],[182041,121,17,1,0],[182042,46,21,1,0],[182044,248,9,1,0],[182045,67,11,1,0],[182046,41,13,1,0],[182400,164,95,1,0],[182401,146,87,1,0],[182402,147,77,1,0],[182403,206,83,1,0],[182404,159,68,1,0],[182405,159,67,1,0],[182406,193,68,1,0],[182407,176,69,1,2],[182408,138,55,1,0],[182409,135,47,1,0],[182410,206,39,1,0],[182411,152,32,1,0],[184781,173,44,1,0],[184782,206,44,1,0],[184783,279,47,1,0],[184784,180,42,1,0],[184786,268,37,1,0],[184787,257,40,1,0],[184788,211,30,1,0],[184789,194,35,1,0],[184790,238,33,1,0],[184791,170,27,1,0],[184792,167,25,1,0],[184795,265,27,1,0],[184796,257,22,1,0],[184797,166,5,1,0],[186088,164,115,1,0],[186089,62,119,1,0],[186090,57,119,1,0],[186091,4,124,1,0],[186092,114,116,1,1],[186093,104,111,1,0],[186094,91,112,1,0],[186095,221,106,1,0],[186096,219,105,1,0],[186097,265,109,1,0],[186098,191,110,1,0],[186099,234,108,1,0],[186100,227,106,1,0],[186101,78,104,1,1],[186102,65,110,1,0],[186103,27,106,1,0],[186104,199,101,1,0],[186105,276,100,1,0],[186106,272,101,1,0],[186107,256,102,1,0],[186108,251,97,1,0],[186109,102,102,1,0],[187815,152,203,1,0],[187816,131,200,1,0],[187817,27,209,1,0],[187818,163,201,1,0],[187819,213,198,1,0],[187820,117,198,1,0],[187821,109,201,1,0],[187822,34,199,1,0],[187823,19,203,1,0],[187824,136,196,1,0],[187825,198,196,1,0],[187826,181,191,1,0],[187827,172,195,1,0],[187828,243,196,1,0],[187829,166,195,1,0],[187830,220,192,1,0],[187831,261,194,1,0],[187832,197,190,1,0],[187833,143,187,1,0],[187834,91,195,1,0],[187835,73,196,1,0],[187836,181,183,1,0],[187837,198,186,1,0],[187838,43,193,1,0],[187839,39,190,1,0],[187840,277,188,1,0],[187841,120,189,1,0],[187842,64,187,1,0],[187843,68,186,1,0],[187844,163,181,1,0],[187845,165,180,1,0],[187846,10,187,1,0],[187847,212,179,1,0],[187848,139,176,1,0],[187849,212,178,1,0],[187850,194,180,1,0],[187851,233,177,1,0],[187852,122,180,1,0],[187853,110,182,1,0],[187854,86,179,1,0],[187855,85,177,1,0],[187856,34,177,1,0],[187857,161,175,1,0],[187858,212,174,1,0],[187859,20,177,1,0],[187860,17,176,1,0],[187861,13,177,1,0],[187862,188,170,1,0],[187863,257,173,1,0],[187864,251,171,1,0],[187866,166,79,1,0],[187867,193,61,1,0],[187868,250,38,1,0],[187871,264,135,4,0],[181998,137,31,1,3],[181999,126,30,1,3],[182000,147,28,1,3],[182001,120,34,1,3],[182036,246,26,1,3],[182037,59,31,1,3],[182043,276,10,1,3],[182047,275,1,1,3],[184785,178,40,1,3],[184793,268,30,1,3]]}})

            # [182038,258,27,1,0] ==> [오랑캐ID, X좌표, Y좌표, 별, 공격횟수]

            # 만약 findall 리스트 item수가 0이면 루프 탈출 후 return interval

            get_orang_xy_url = '/game/api_fav.php?jsonpcallback=jsonp' + get_time() + '&_=' + get_time() + '&key=' + base_token + '&act=getfavnpc&cat=2&_l=kr&_p=SG-IPHONE-KR{}HTTP/1.1'.format(urllib.parse.quote(' '))

            html_source = get_html_response(get_orang_xy_url, 2)

            if html_source == '::ERROR::':

                if err_cnt <= 3:

                    err_cnt += 1

                    print('[04]Error발생')

                    timesleep(5)

                    continue

                else:

                    print('3회 이상 에러가 발생하여 자동 사냥을 중단합니다!!')

                    return -1

            if '"code":0' in html_source:

                find_orang_xy = re.findall('\[\d+,(\d+),(\d+),' + str(type_orang) + ',[0-2]', html_source)

                if find_orang_xy:

                    attack_x = find_orang_xy[0][0]

                    attack_y = find_orang_xy[0][1]

                    print('공격좌표 추출 완료 : ' + attack_x + '/' + attack_y)

                    next_ip = 'next'

                    rand_timesleep()

                else:

                    print('더이상 공격할 좌표가 없어 자동사냥 작업을 종료 합니다.')

                    next_ip = 'exit_auto_attack'

            else:

                if err_cnt <= 3:

                    err_cnt += 1

                    print('[05]Error발생')

                    timesleep(5)

                    continue

                else:

                    print('3회 이상 에러가 발생하여 자동 사냥을 중단합니다!!')

                    return -1

        

        if next_ip == 'next':

            # 3. 공격좌표 이상유무 파악!!

            # GET /game/armament_action_do_api.php?jsonpcallback=jsonp1334359483816&_=1334372353885&key=ac91d18916be985c476e6a4bbfb7bd56&city=23764&act=anum&x=78&y=104&_l=kr&_p=SG-IPHONE-KR HTTP/1.1

            # jsonp1334424047624({"code":0,"ret":0})

            # "code":0,"ret":0 응답이 이거면 진행 아니면 다음루프 continue

            is_target_ok_url = '/game/armament_action_do_api.php?jsonpcallback=jsonp' + get_time() + '&_=' + get_time() + '&key=' + base_token + '&city=' + city_id + '&act=anum&x=' + attack_x + '&y=' + attack_y + '&_l=kr&_p=SG-IPHONE-KR{}HTTP/1.1'.format(urllib.parse.quote(' '))

            #print('is_target_ok_url :' + is_target_ok_url)

            html_source = get_html_response(is_target_ok_url, 2)

            if html_source == '::ERROR::':

                if err_cnt <= 3:

                    err_cnt += 1

                    print('[06]Error발생')

                    timesleep(5)

                    continue

                else:

                    print('3회 이상 에러가 발생하여 자동 사냥을 중단합니다!!')

                    return -1

            if '"code":0' in html_source:

                next_ip = 'next'

                print('좌표[' + attack_x + '/' + attack_y + '] 공격가능!!')

                rand_timesleep()

            else:

                if err_cnt <= 3:

                    err_cnt += 1

                    print('[08]Error발생')

                    timesleep(5)

                    continue

                else:

                    print('3회 이상 에러가 발생하여 자동 사냥을 중단합니다!!')

                    return -1


        if next_ip == 'next':

            # 4. 병력 정보

            # GET /game/soldier_educate_api.php?jsonpcallback=jsonp1334359483817&_=1334372353891&key=ac91d18916be985c476e6a4bbfb7bd56&city=23764&_l=kr&_p=SG-IPHONE-KR HTTP/1.1

            # jsonp1334424148283({"code":0,"ret":{"soldiers":[[1,0,1],[2,110,1],[3,0,1],[4,0,1],[5,0,1],[6,0,1],[7,0,1],[8,0,1],[9,0,0],[10,0,1],[11,500,1],[12,0,0],[13,0,1],[14,0,0],[15,4500,1]],"space":5390,"head":7103,"def":1,"next":[16,22],"f":107896}})

            # type_soldier가 num_soldier만큼 있으면 통과 없으면 5, 6, 7, 8 스킵후 interval 만큼 대기!! type_soldier, num_soldier

            get_soldier_num_url = '/game/soldier_educate_api.php?jsonpcallback=jsonp' + get_time() + '&_=' + get_time() + '&key=' + base_token + '&city=' + city_id + '&_l=kr&_p=SG-IPHONE-KR{}HTTP/1.1'.format(urllib.parse.quote(' '))

            html_source = get_html_response(get_soldier_num_url, 2)

            if html_source == '::ERROR::':

                if err_cnt <= 3:

                    err_cnt += 1

                    print('[09]Error발생')

                    timesleep(5)

                    continue

                else:

                    print('3회 이상 에러가 발생하여 자동 사냥을 중단합니다!!')

                    return -1

            if '"code":0' in html_source:

                find_soldier_num = re.findall('\['+ str(type_soldier) + ',(\d+),[01]\]', html_source)

                if find_soldier_num:

                    my_soldier_num = find_soldier_num[0]

                    

                    if int(my_soldier_num) >= int(num_soldier):

                        # 병력이 충분하면.. 통과

                        print('병력 보유[' + str(my_soldier_num) + '] 공격 진행!!')

                        next_ip = 'next'

                        rand_timesleep()

                    else:

                        # 병력이 적으면!! 인터벌 대기

                        print('더이상 공격할 병력이 없어 다음 인터벌 까지 대기합니다.')

                        next_ip = 'wait_interval'

                        rand_timesleep()

                else:

                    print('더이상 공격할 병력이 없어 다음 인터벌 까지 대기합니다.')

                    next_ip = 'wait_interval'

                    rand_timesleep()

            else:

                if err_cnt <= 3:

                    err_cnt += 1

                    print('[10]Error발생')

                    timesleep(5)

                    continue

                else:

                    print('3회 이상 에러가 발생하여 자동 사냥을 중단합니다!!')

                    return -1

        

        if next_ip == 'next':

            # 5. 통솔 장수 선택

            # GET /game/gen_conscribe_api.php?jsonpcallback=jsonp1334359483818&_=1334372360888&key=ac91d18916be985c476e6a4bbfb7bd56&city=23764&action=gen_list&extra=1&_l=kr&_p=SG-IPHONE-KR HTTP/1.1

            # jsonp1334424202909({"code":0,"ret":{"hero":[{"id":89862,"gid":189,"p":33,"i":41,"c1":18,"f":80,"g":13,"c2":900,"fy":0,"s":0,"e":16,"w":1,"tw":8,"tl":31,"ex":118887,"te":565620,"np":0,"ni":0,"nc1":0,"nc2":250,"ns":0,"ncd":0,"pr":39000},{"id":93364,"gid":179,"p":30,"i":55,"c1":16,"f":75,"g":13,"c2":823,"fy":0,"s":0,"e":16,"w":0,"tw":8,"tl":17,"ex":10843,"te":565620,"np":0,"ni":0,"nc1":0,"nc2":180,"ns":0,"ncd":0,"pr":39000},{"id":96018,"gid":207,"p":59,"i":12,"c1":33,"f":75,"g":13,"c2":830,"fy":0,"s":0,"e":16,"w":1,"tw":7,"tl":26,"ex":291604,"te":565620,"np":0,"ni":0,"nc1":0,"nc2":180,"ns":0,"ncd":0,"pr":39000},{"id":97215,"gid":177,"p":31,"i":49,"c1":29,"f":73,"g":13,"c2":845,"fy":0,"s":0,"e":16,"w":0,"tw":7,"tl":29,"ex":31237,"te":565620,"np":0,"ni":0,"nc1":0,"nc2":180,"ns":0,"ncd":0,"pr":39000},{"id":97340,"gid":186,"p":32,"i":43,"c1":19,"f":75,"g":13,"c2":844,"fy":0,"s":0,"e":16,"w":1,"tw":2,"tl":23,"ex":3042,"te":565620,"np":8,"ni":15,"nc1":11,"nc2":419,"ns":0,"ncd":0,"pr":39000},{"id":98342,"gid":126,"p":33,"i":53,"c1":26,"f":30,"g":12,"c2":879,"fy":0,"s":0,"e":16,"w":0,"tw":18,"tl":27,"ex":221902,"te":257100,"np":15,"ni":45,"nc1":19,"nc2":759,"ns":0,"ncd":0,"pr":36000},{"id":104287,"gid":185,"p":11,"i":42,"c1":13,"f":60,"g":12,"c2":617,"fy":0,"s":0,"e":16,"w":0,"tw":0,"tl":3,"ex":99753,"te":257100,"np":0,"ni":0,"nc1":0,"nc2":0,"ns":0,"ncd":0,"pr":36000},{"id":109341,"gid":73,"p":44,"i":54,"c1":32,"f":15,"g":15,"c2":830,"fy":0,"s":0,"e":16,"w":2,"tw":2,"tl":10,"ex":241832,"te":2737601,"np":0,"ni":0,"nc1":0,"nc2":30,"ns":0,"ncd":0,"pr":45000},{"id":111918,"gid":45,"p":37,"i":54,"c1":26,"f":55,"g":10,"c2":854,"fy":0,"s":0,"e":16,"w":0,"tw":0,"tl":0,"ex":26823,"te":53119,"np":0,"ni":0,"nc1":0,"nc2":180,"ns":0,"ncd":0,"pr":30000}]}})

            # jsonp1334705981745({"code":0,"ret":{"hero":[{"id":89862,"gid":189,"p":33,"i":41,"c1":18,"f":85,"g":13,"c2":910,"fy":0,"s":0,"e":16,"w":0,"tw":10,"tl":32,"ex":443066,"te":565620,"np":0,"ni":0,"nc1":0,"nc2":260,"ns":0,"ncd":0,"pr":39000},{"id":93364,"gid":179,"p":30,"i":55,"c1":16,"f":75,"g":13,"c2":823,"fy":0,"s":0,"e":16,"w":1,"tw":9,"tl":17,"ex":332048,"te":565620,"np":0,"ni":0,"nc1":0,"nc2":180,"ns":0,"ncd":0,"pr":39000},{"id":96018,"gid":207,"p":62,"i":12,"c1":33,"f":75,"g":14,"c2":868,"fy":0,"s":0,"e":16,"w":1,"tw":7,"tl":26,"ex":47550,"te":1244364,"np":0,"ni":0,"nc1":0,"nc2":180,"ns":0,"ncd":0,"pr":42000},{"id":97215,"gid":177,"p":31,"i":49,"c1":29,"f":73,"g":13,"c2":845,"fy":0,"s":0,"e":16,"w":0,"tw":8,"tl":31,"ex":352312,"te":565620,"np":0,"ni":0,"nc1":0,"nc2":180,"ns":0,"ncd":0,"pr":39000},{"id":97340,"gid":186,"p":32,"i":43,"c1":19,"f":75,"g":13,"c2":844,"fy":0,"s":0,"e":16,"w":2,"tw":3,"tl":23,"ex":323906,"te":565620,"np":8,"ni":15,"nc1":11,"nc2":419,"ns":0,"ncd":0,"pr":39000},{"id":98342,"gid":126,"p":33,"i":57,"c1":26,"f":35,"g":13,"c2":917,"fy":0,"s":0,"e":16,"w":4,"tw":22,"tl":27,"ex":284646,"te":565620,"np":15,"ni":45,"nc1":19,"nc2":759,"ns":0,"ncd":0,"pr":39000},{"id":104287,"gid":185,"p":11,"i":45,"c1":13,"f":60,"g":13,"c2":653,"fy":0,"s":0,"e":16,"w":0,"tw":0,"tl":4,"ex":162018,"te":565620,"np":0,"ni":0,"nc1":0,"nc2":0,"ns":0,"ncd":0,"pr":39000},{"id":109341,"gid":73,"p":44,"i":54,"c1":32,"f":20,"g":15,"c2":950,"fy":0,"s":0,"e":16,"w":0,"tw":2,"tl":12,"ex":561262,"te":2737601,"np":0,"ni":0,"nc1":0,"nc2":150,"ns":0,"ncd":0,"pr":45000}]}})

            # 만약 findall 리스트 item수가 0이면 10번으로

            # 리스트 item은 있으나 c2(통솔력)가 딸리는 장수들 뿐이면 역시 10번으로

            # 리스트item은 있으나  e(기력)이 딸리는 장수들 뿐이면 역시 10번으로

            

            get_gen_id_url = '/game/gen_conscribe_api.php?jsonpcallback=jsonp' + get_time() + '&_=' + get_time() + '&key=' + base_token + '&city=' + city_id + '&action=gen_list&extra=1&_l=kr&_p=SG-IPHONE-KR{}HTTP/1.1'.format(urllib.parse.quote(' '))

            html_source = get_html_response(get_gen_id_url, 2)

            if html_source == '::ERROR::':

                if err_cnt <= 3:

                    err_cnt += 1

                    print('[11]Error발생')

                    timesleep(5)

                    continue

                else:

                    print('3회 이상 에러가 발생하여 자동 사냥을 중단합니다!!')

                    return -1

            if '"code":0' in html_source:

                #find_gen_id = re.findall('"gid":(\d+),"p":\d+,"i":\d+,"c1":\d+,"f":\d+,"g":\d+,"c2":([' + str(num_soldier)[0] + '-9]\d*),', html_source)

                find_gen_id = re.findall('"gid":(\d+),"p":\d+,"i":\d+,"c1":\d+,"f":\d+,"g":\d+,"c2":(\d+),', html_source)

                selected_gen_id = ''

                if find_gen_id:

                    for loop_idx in find_gen_id:

                        if int(loop_idx[1]) >=  num_soldier:

                            selected_gen_id = loop_idx[0]

                            break

                        else:

                            selected_gen_id = ''

                    

                    if selected_gen_id != '':

                        print('통솔 장수 ID 추출 완료[' + str(selected_gen_id) + '] 공격 진행!!')

                        next_ip = 'next'

                        rand_timesleep()

                    else:

                        print('더이상 공격할 장수가 없어 다음 인터벌 까지 대기합니다.')

                        next_ip = 'wait_interval'

                        rand_timesleep()

                else:

                    print('더이상 공격할 장수가 없어 다음 인터벌 까지 대기합니다.')

                    next_ip = 'wait_interval'

                    rand_timesleep()

            else:

                if err_cnt <= 3:

                    err_cnt += 1

                    print('[12]Error발생')

                    timesleep(5)

                    continue

                else:

                    print('3회 이상 에러가 발생하여 자동 사냥을 중단합니다!!')

                    return -1


        if next_ip == 'next':

            # 6. 공격정보 상세

            # GET /game/armament_action_do_api.php?jsonpcallback=jsonp1334359483819&_=1334372374733&key=ac91d18916be985c476e6a4bbfb7bd56&city=23764&action=do_war&attack_type=7&gen=189&area=78&area_x=104&soldier_num15=500&_l=kr&_p=SG-IPHONE-KR HTTP/1.1

            # jsonp1334424277458({"code":0,"ret":{"carry":396000,"cost_food":90000,"cost_wood":0,"cost_iron":0,"cost_gold":0,"distance":20160,"travel_sec":540}})

            # 음식소요와 공격명령 파라메터 생성!!

            # 타음 인터벌 맥스값 계산 세트!! 공식 : (travel_sec + 60 * 2)가  inteval_sec보다 크면 inteval_sec 교체

            attack_info_url = '/game/armament_action_do_api.php?jsonpcallback=jsonp' + get_time() + '&_=' + get_time() + '&key=' + base_token + '&city=' + city_id + '&action=do_war&attack_type=7&gen=' + selected_gen_id + '&area=' + attack_x + '&area_x=' + attack_y + '&soldier_num' + str(type_soldier) + '=' + str(num_soldier) + '&_l=kr&_p=SG-IPHONE-KR{}HTTP/1.1'.format(urllib.parse.quote(' '))

            html_source = get_html_response(attack_info_url, 2)

            if html_source == '::ERROR::':

                if err_cnt <= 3:

                    err_cnt += 1

                    print('[13]Error발생')

                    timesleep(5)

                    continue

                else:

                    print('3회 이상 에러가 발생하여 자동 사냥을 중단합니다!!')

                    return -1

            if '"code":0' in html_source:

                attack_info = re.search('"carry":(\d+),"cost_food":(\d+),"cost_wood":(\d+),"cost_iron":(\d+),"cost_gold":(\d+),"distance":(\d+),"travel_sec":(\d+)',html_source).group()

                attack_info = '&' + attack_info.replace('"', '').replace(':', '=').replace(',', '&')

                food_per_attack     = int(re.search('cost_food":(\d+),', html_source).group(1))

                interval_per_attack = int(re.search('travel_sec":(\d+)}', html_source).group(1)) * 2

                print('도시보유 식량 : ' + city_tot_food + ', 공격소요 식량 : ' + str(food_per_attack))

                print('공격소요시간(복귀시간포함) : ' + str(interval_per_attack))


                if int(city_tot_food) < int(food_per_attack):

                    # 식량교환(1골드당 7.6923 식량)

                    need_chg_tot_gold = int(food_per_attack / 7.6923)

                    # 계산된 골드 보다 10골드 더 교환 요건 걍 내맴

                    need_chg_tot_gold += 100

                    # 현재 도시의 돈이 need_chg_tot_gold보다 적으면 진행 불가 인터벌 대기!!

                    if city_tot_money < need_chg_tot_gold:

                        print('도시에 다음 전투 식량 교환을 위한 동전이 부족하여 다음 인터벌 까지 대기합니다.')

                        next_ip = 'wait_interval'

                        rand_timesleep()

                    else:

                        ret_do_g2f = do_g2f(need_chg_tot_gold, city_id)

                        if ret_do_g2f == '::ERROR::':

                            print('식량자원 교환에 실패하여 자동사냥을 중지합니다!!')

                            next_ip = 'exit_auto_attack'

                        else:

                            rand_timesleep()

                            print('식량자원 교환 성공!! 공격 진행!!')

                            next_ip = 'next'

                else:

                    next_ip = 'next'

                    print('식량자원 요건 충족!! 공격 진행!!')

                    rand_timesleep()

            else:

                if err_cnt <= 3:

                    err_cnt += 1

                    print('[14]Error발생')

                    timesleep(5)

                    continue

                else:

                    print('3회 이상 에러가 발생하여 자동 사냥을 중단합니다!!')

                    return -1


        if next_ip == 'next':

            # 7. 도시자원 정보(의미 없음)

            # GET /game/get_cityinfo_api.php?jsonpcallback=jsonp1334359484911&_=1334372387271&key=ac91d18916be985c476e6a4bbfb7bd56&city=23764&_l=kr&_p=SG-IPHONE-KR HTTP/1.1

            # jsonp1334424402425({"code":0,"ret":{"city":[27,183,764129,159000,1276893,159000,1214668,159000,1980380,159000,6656,8125,10,12,11,26,17,21,19,19,1,4,14,[{"id":52066,"itemid":166,"secs":502596},{"id":52201,"itemid":126,"secs":14202}],0],"grade":43,"money":100}})

            get_city_info_url = '/game/get_cityinfo_api.php?jsonpcallback=jsonp' + get_time() + '&_=' + get_time() + '&key=' + base_token + '&city=' + city_id + '&_l=kr&_p=SG-IPHONE-KR{}HTTP/1.1'.format(urllib.parse.quote(' '))

            html_source = get_html_response(get_city_info_url, 2)

            if html_source == '::ERROR::':

                if err_cnt <= 3:

                    err_cnt += 1

                    print('[15]Error발생')

                    timesleep(5)

                    continue

                else:

                    print('3회 이상 에러가 발생하여 자동 사냥을 중단합니다!!')

                    return -1

            if '"code":0' in html_source:

                next_ip = 'next'

                rand_timesleep()

            else:

                if err_cnt <= 3:

                    err_cnt += 1

                    print('[16]Error발생')

                    timesleep(5)

                    continue

                else:

                    print('3회 이상 에러가 발생하여 자동 사냥을 중단합니다!!')

                    return -1


        if next_ip == 'next':        

            # 8. 공격명령!!

            # GET /game/armament_action_task_api.php?jsonpcallback=jsonp1334359483820&_=1334372411619&key=ac91d18916be985c476e6a4bbfb7bd56&city=23764&action=war_task&attack_type=7&gen=189&area=78&area_x=104&soldier_num15=500&_l=kr&_p=SG-IPHONE-KR&carry=396000&cost_food=90000&cost_wood=0&cost_iron=0&cost_gold=0&distance=7440&travel_sec=180 HTTP/1.1

            # jsonp1334424477066({"code":0,"ret":{"cd":[{"id":6334289,"cdtype":4,"target":7,"owner":189,"secs":540,"ret":0,"ext":"166\/79"}]}})

            do_attack_url = '/game/armament_action_task_api.php?jsonpcallback=jsonp' + get_time() + '&_=' + get_time() + '&key=' + base_token + '&city=' + city_id + '&action=war_task&attack_type=7&gen=' + selected_gen_id + '&area=' + attack_x + '&area_x=' + attack_y + '&soldier_num' + str(type_soldier) + '=' + str(num_soldier) + '&_l=kr&_p=SG-IPHONE-KR' + attack_info + '{}HTTP/1.1'.format(urllib.parse.quote(' '))

            html_source = get_html_response(do_attack_url, 2)

            if html_source == '::ERROR::':

                if err_cnt <= 3:

                    err_cnt += 1

                    print('[15]Error발생')

                    timesleep(5)

                    continue

                else:

                    print('3회 이상 에러가 발생하여 자동 사냥을 중단합니다!!')

                    return -1

            if '"code":0' in html_source:

                print('좌표[' + attack_x + '/' + attack_y + '] 공격완료!!')

                # 에러카운트 초기화

                err_cnt = 0

                # 롱텀 인터벌 판별 및 스왑

                if interval_per_attack > inteval_sec:

                    print('현재 인터벌[' + str(inteval_sec) + ']보다 큰 인터벌[' + str(interval_per_attack) + ']발견!! 스왑인터벌')

                    inteval_sec = interval_per_attack

                # 식량교환(1골드당 7.6923 식량)

                need_chg_tot_gold = int(food_per_attack / 7.6923)

                # 계산된 골드 보다 10골드 더 교환 요건 걍 내맴

                need_chg_tot_gold += 100

                

                # 현재 도시의 돈이 need_chg_tot_gold보다 적으면 진행 불가 인터벌 대기!!

                if int(city_tot_money) < int(need_chg_tot_gold):

                    print('도시에 다음 전투 식량 교환을 위한 동전이 부족하여 다음 인터벌 까지 대기합니다.')

                    next_ip = 'wait_interval'

                    rand_timesleep()

                else:

                    ret_do_g2f = do_g2f(need_chg_tot_gold, city_id)

                    if ret_do_g2f == '::ERROR::':

                        print('식량자원 교환에 실패하여 자동사냥을 중지합니다!!')

                        next_ip = 'exit_auto_attack'

                    else:

                        rand_timesleep()

                        print('소비 식량자원 보충 성공!!')

                        next_ip = 'next'

            else:

                if err_cnt <= 3:

                    err_cnt += 1

                    print('[16]Error발생')

                    timesleep(5)

                    continue

                else:

                    print('3회 이상 에러가 발생하여 자동 사냥을 중단합니다!!')

                    return -1

                

        # 10. 1번으로 반복

        if next_ip == 'next':

            continue

        

        # 11. 도시 사냥 종료 인터벌 대기!!

        if next_ip == 'wait_interval':

            return inteval_sec

        

        # 12. 사냥불가로 인한 사냥 종료(해당 도시는 더이상 공격 안함 리스트에서 팝시킴)

        if next_ip == 'exit_auto_attack':

            return -1


def get_time():

    return str(int(time.time() * 1000))


def rand_timesleep():

    rand_sec = random.randrange(1,2)

    #print('오토검출 방지 대기 : ' + str(rand_sec) + '초')

    time.sleep(rand_sec)

    return


def timesleep(interval_sec):

    print('대기명령 : ' + str(interval_sec) + '초...')

    time.sleep(interval_sec)

    return


def make_cookie():

    gen_cookie = ''

    for l_idx in range(0,32):

        rand_num = random.randrange(1,1000)

        if rand_num > 500:

            gen_cookie += chr(random.randrange(97, 102))

        else:

            gen_cookie += chr(random.randrange(48, 57))

    

    return gen_cookie


def get_html_response(send_url, attempt_type, decode_type = 'utf-8'):

    err_cnt = 0

    

    while True:

        try:

            if attempt_type == 1:

                # 메인 호스트 호출

                conn = http.client.HTTPConnection('m.tapsg.com', 80)

            elif attempt_type == 2:

                # 사용자 서버 호스트 호출

                conn = http.client.HTTPConnection(base_user_host, 80)

            elif attempt_type == 3:

                conn = http.client.HTTPConnection('129.100.170.100', 8181)

            conn.putrequest('GET', send_url)

            

            if attempt_type == 1:

                # 메인 호스트 호출

                conn.putheader('Host','m.tapsg.com')

                conn.putheader('User-Agent','{}/1.10 CFNetwork/548.0.4 Darwin/11.0.0'.format(urllib.parse.quote('손바닥 삼국지')))        

            elif attempt_type == 2:

                # ID종속 서버 호스트 호출

                conn.putheader('Host',base_user_host)

                conn.putheader('User-Agent','Mozilla/5.0 (iPhone; CPU iPhone OS 5_0_1 like Mac OS X) AppleWebKit/534.46 (KHTML, like Gecko) Mobile/9A405')

            elif attempt_type == 3:

                conn.putheader('Host','129.100.170.100:8181')

                conn.putheader('User-Agent','Mozilla/5.0 (iPhone; CPU iPhone OS 5_0_1 like Mac OS X) AppleWebKit/534.46 (KHTML, like Gecko) Mobile/9A405')

            conn.putheader('Accept','*/*')

            conn.putheader('Accept-Language','ko-kr')

            conn.putheader('Accept-Encoding','gzip, deflate')

            conn.putheader('Cookie','phpbb3_surfz_k=; phpbb3_surfz_sid=' + base_cookie + '; phpbb3_surfz_u=1')

            conn.putheader('Connection','keep-alive')

            conn.putheader('','')

            conn.endheaders()

            resp = conn.getresponse()

            if str(resp.status).strip() != '200':

                if attempt_type == 3:

                    print('허가되지 않은 장소에서의실행 요청입니다!!')

                    sys.exit()

                print(str(send_url) + ' 페이지에 접속하는데에 실패하였습니다.')

                conn.close()

                resp.close()        

                return '::ERROR::'

            else:

                ret_html_bytes = resp.read()

                ret_html_str = str(ret_html_bytes.decode(decode_type))

                conn.close()

                resp.close()

                return ret_html_str

        except Exception:

            if attempt_type == 3:

                print('허용되지 않은 장소에서의 실행입니다!! 프로그램을 종료합니다!!')

                sys.exit()

            if err_cnt <= 3:

                print('서버연결 응답없음!! 재시도[' + str(err_cnt) + '회')

                err_cnt += 1

                timesleep(30)

                continue

            else:

                print('손바닥 삼국지 서버로 부터 응답이 없습니다. 프로그램 종료!!')

                sys.exit()


def attempt_login():

    print('Payment 체크..')

    payment_chk_url = '/dopayment.php?user=&act=query{}HTTP/1.1'.format(urllib.parse.quote(' '))

    html_source = get_html_response(payment_chk_url, 1)

    if html_source != '::ERROR::':

        print('성공')

    else:

        print('손바닥 삼국지 서버 접속에 실패하였습니다!!\n잠시후 다시 시도하여주세요!!')

        return '::ERROR::'

    

    del(payment_chk_url)

    return 0


def do_g2f(gold_value, city_id):

    # 교환실행

    do_g2f_url = '/game/local_market_api.php?jsonpcallback=jsonp' + get_time() + '&_=' + get_time() + '&key=' + base_token + '&city=' + city_id + '&reso_put=giveput&g2f=' + str(gold_value) + '&_l=kr&_p=SG-IPHONE-KR{}HTTP/1.1'.format(urllib.parse.quote(' '))

    html_source = get_html_response(do_g2f_url, 2)

    if html_source == '::ERROR::':

        return '::ERROR::'

    if '"code":0' in html_source:

        print('[' + str(gold_value) + ']동전을 [' + str(int(gold_value * 7.6923)) + ']식량으로 교환 하는데 성공 하였습니다!!')

        return 'OK'

    else:

        print('동전 ==> 식량 교환에 실패하였습니다!!')

        print('Error Code : ' + html_source)

        return '::ERROR::'

    

def get_soldier(city_id, soldier_type):

    # 병영정보

    soldier_url = '/game/soldier_educate_api.php?jsonpcallback=jsonp' + get_time() + '&_=' + get_time() + '&key=' + base_token + '&city=' + city_id + '&_l=kr&_p=SG-IPHONE-KR{}HTTP/1.1'.format(urllib.parse.quote(' '))

    html_source = get_html_response(soldier_url, 2)

    if html_source == '::ERROR::':

        return '::ERROR::'


    if '"code":0' in html_source:

        soldier_num = re.findall('\[' + str(soldier_type) + ',(\d+),\d+\]', html_source)

        if soldier_num:

            soldier_num = int(soldier_num[0])

        else:

            soldier_num = 0

            

        return soldier_num

    else:

        print('사용자 병력 정보 추출에 실패하였습니다!!')

        print('Error Code : ' + html_source)

        return -1


def do_scout(point_x, point_y):

    # 척후병 보유 여부 판단!!

    soldier_num = get_soldier(base_city_id, '2')

    if soldier_num > 0:

        print('척후병 보유수 : ' + str(soldier_num))

    elif soldier_num == 0:

        print('척후병 보유병사가 없으므로 정찰을 진행하지 않습니다!!')

        return 'SKIP'

    else:

        print('척후병 보유수를 가져오는데 실패하였습니다!!')

        return '::ERROR::'

    rand_timesleep()

    

    # 정찰사전정보 수집

    # 본진으로 부터 해당 좌표까지의 거리, 소요자원, 시간, 해당좌표의 ID값 추출 

    scout_info_url = '/game/armament_action_do_api.php?jsonpcallback=jsonp' + get_time() + '&_=' + get_time() + '&key=' + base_token + '&city=' + base_city_id + '&action=do_war&attack_type=3&tai_num=1&area=' + str(point_x) + '&area_x=' + str(point_y) + '&_l=kr&_p=SG-IPHONE-KR{}HTTP/1.1'.format(urllib.parse.quote(' '))

    html_source = get_html_response(scout_info_url, 2)

    if html_source == '::ERROR::':

        return '::ERROR::'

    if '"code":0' in html_source:

        scout_info = re.search('"carry":(\d+),"cost_food":(\d+),"cost_wood":(\d+),"cost_iron":(\d+),"cost_gold":(\d+),"distance":(\d+),"travel_sec":(\d+)',html_source).group()

        scout_info = '&' + scout_info.replace('"', '').replace(':', '=').replace(',', '&')

        cost_food = re.search('cost_food":(\d+),', html_source).group(1)

        print('정찰소요 식량 : ' + str(cost_food))

    else:

        print('정찰지[' + point_x + '/' + point_y + '] 정찰사전정보 수집실패!!')

        print('Error Code : ' + html_source)

        return '::ERROR::'

    rand_timesleep()

    

    # 도시정보 호출 후 식량자원량 추출

    city_resource = get_city_resource(base_city_id)

    if city_resource:

        if city_resource == '::ERROR::':

            return '::ERROR::'

        else:

            city_food = city_resource[0][1]

    else:

        return '::ERROR::'

    rand_timesleep()

    

    # 충분한 식량이 있는지 판단!!

    if int(cost_food) > int(city_food):

        # 없으면 스킵!!

        return '::ERROR::'


    # 정찰

    scout_url = '/game/armament_action_task_api.php?jsonpcallback=jsonp' + get_time() + '&_=' + get_time() + '&key=' + base_token + '&city=' + base_city_id + '&action=war_task&attack_type=3&tai_num=1&area=' + str(point_x) + '&area_x=' + str(point_y) + '&_l=kr&_p=SG-IPHONE-KR' + scout_info + '{}HTTP/1.1'.format(urllib.parse.quote(' '))

    html_source = get_html_response(scout_url, 2)

    if html_source == '::ERROR::':

        return '::ERROR::'

    if '"code":0' in html_source:

        target_id = re.search('"id":(\d+),"cdtype"', html_source).group(1)

        print('정찰지[' + point_x + '/' + point_y + '] ID : ' + target_id + ' : 정찰시도 성공!!')

        return 'OK'

    else:

        print('정찰지[' + point_x + '/' + point_y + '] ID : ' + target_id + ' : 정찰시도 실패!!')

        print('Error Code : ' + html_source)

        return '::ERROR::'

    rand_timesleep()


def get_city_resource(city_id):

    # 도시정보  

    cityinfo_url = '/game/get_cityinfo_api.php?jsonpcallback=jsonp' + get_time() + '&_=' + get_time() + '&key=' + base_token + '&city=' + city_id + '&_l=kr&_p=SG-IPHONE-KR{}HTTP/1.1'.format(urllib.parse.quote(' '))

    html_source = get_html_response(cityinfo_url, 2)

    if html_source == '::ERROR::':

        return '::ERROR::'

    if '"code":0' in html_source:

        city_rs = re.findall('city":\[\d+,\d+,(\d+),\d+,(\d+),\d+,(\d+),\d+,(\d+),', html_source)

        print('동전 : ' + city_rs[0][0] + ', 식량 : ' + city_rs[0][1] + ', 목재 : ' + city_rs[0][2] + ', 철광석 : ' + city_rs[0][3])

        return city_rs

    else:

        print('사용자 정보 추출에 실패하였습니다!!')

        print('Error Code : ' + html_source)

        return '::ERROR::'


def scan_area_all(max_findout_cnt,orangke_type, input_point_x, input_point_y):

        #====지역스캔

        findout_cnt = 1

        err_cnt = 0

        recp_orang = re.compile('\[(\d+),(\d+),([' + str(orangke_type) + ']{1}),\[(\d+)]]')

        recp_food  = re.compile('\[(\d+),(\d+),103,\[(\d+),(\d+),"",""\]\]')

        # 이전 스캔데이터들이 존재하면 파일명을 변경해 백업한다.

        if os.access('orang_data.dat', os.F_OK):

            os.rename('orang_data.dat', 'old_orang_data' + str(time.strftime('%y%m%d%H%M%S')) + '.dat')

        if os.access('food_data.dat', os.F_OK):

            os.rename('food_data.dat', 'old_food_data' + str(time.strftime('%y%m%d%H%M%S')) + '.dat')

        f_orang = open('orang_data.dat', 'w')

        f_food  = open('food_data.dat', 'w')

        for point_y in range(input_point_y, 278, 7):

                for point_x in range(input_point_x, 278, 7):

                        detail_url = '/game/api_world_map.php?jsonpcallback=jsonp' + get_time() + '&_=' + get_time() + '&key=' + base_token + '&x=' + str(point_x) + '&y=' + str(point_y) + '&_l=kr&_p=SG-IPHONE-KR{}HTTP/1.1'.format(urllib.parse.quote(' '))

                        token_str = get_html_response(detail_url, 2)

                        rand_timesleep()

                        if token_str == '::ERROR::':

                            return '::ERROR::'

                        if findout_cnt <= max_findout_cnt:

                            if '"code":0' not in token_str:

                                    print('[지도스캔좌표 : ' + str(point_x) + '/' + str(point_y) + ']의 스캔에 실패하였습니다.\r\n이 지역을 제외하고 다음지역을 스캔합니다!!')

                                    if err_cnt > 3:

                                            return '::ERROR::'

                                    else:

                                            err_cnt += 1

                            else:

                                    # 오랑캐 스캔!!

                                    find_orang_x_y = recp_orang.findall(token_str)

                                    for idx_x_y in find_orang_x_y:

                                        if idx_x_y:

                                            print(list(idx_x_y), end = '')

                                            print(' ' + list(idx_x_y)[0] + '/' + list(idx_x_y)[1] + ' : 오랑캐 좌표 발견!!')

                                            # 정찰 시도!!

                                            ret_scout = do_scout(list(idx_x_y)[0], list(idx_x_y)[1])

                                            if ret_scout == 'OK':

                                                f_orang.write('[' + list(idx_x_y)[0] + ',' + list(idx_x_y)[1] + ',정찰시도성공]\n')

                                            else:

                                                f_orang.write('[' + list(idx_x_y)[0] + ',' + list(idx_x_y)[1] + ',정찰시도실패]\n')


                                            findout_cnt += 1

                                    # 식량창고(대) 스캔!!

                                    find_food_x_y = recp_food.findall(token_str)

                                    for idx_x_y in find_food_x_y:

                                        if idx_x_y:

                                            print(list(idx_x_y), end = '')

                                            print(' 미점령 식량창고(대) 좌표 발견!!')

                                            f_food.write(str(idx_x_y) + '\n')

                        else:

                            print('찾은 오랑캐 좌표수 : ' + str(findout_cnt-1) + ', 제한 오랑캐 좌표수 : ' + str(max_findout_cnt) + '\r\n사용자 탐색 제한값에 도달하여 탐색을 중지합니다!!')

                            print('찾아진 오랑캐 좌표가 ''orang_dat.dat''파일로 저장되었습니다!')

                            return '0'

        return '0'

        print('찾아진 오랑캐 좌표가 ''orang_dat.dat''파일로 저장되었습니다!')

        f_orang.close()

        f_food.close()


def get_enemy_info_from_file():

    # 파일오픈..

    try:

        f_new = open('orang_final.dat', 'w')

    except Exception:

        print('오랑캐 좌표 분석을 위한 파일을 여는데 실패하였습니다!!')

        return '::ERROR::'

    

    try:

        # 편지함 뒤지기(의미 없음!!) 

        # 로그패턴을 최대한 실제 어플과 비슷하게 하여 오토 검출을 방해하기 위함

        # (해봐야 맘먹고 찾으면 다 걸리겠지만 ㅋㅋ)

        viewmail_url = '/game/message_api.php?jsonpcallback=jsonp' + get_time() + '&_=' + get_time() + '&key=' + base_token + '&page=1&_l=kr&_p=SG-IPHONE-KR{}HTTP/1.1'.format(urllib.parse.quote(' '))

        html_source = get_html_response(viewmail_url, 2)

        if html_source == '::ERROR::':

            return '::ERROR::'

        if '"code":0' in html_source:

            pass

        else:

            print('정찰 정보를 추출 하는데 실패하였습니다.')

            print('viewmail_url : ' + html_source)

            return '::ERROR::'

        rand_timesleep()

        

        # 정찰결과 리스팅

        scout_info_dat = ''

        while True:

            scout_list_url = '/game/war_result_list_api.php?jsonpcallback=jsonp' + get_time() + '&_=' + get_time() + '&key=' + base_token + '&page=1&type=3&_l=kr&_p=SG-IPHONE-KR{}HTTP/1.1'.format(urllib.parse.quote(' '))

            html_source = get_html_response(scout_list_url, 2)

            if html_source == '::ERROR::':

                return '::ERROR::'

            rand_timesleep()

            if '"code":0' in html_source:

                scout_info_dat = html_source

                # 현재 추출되어진 ID들을 결과함에서 삭제함.. 페이지가 10page 맥스이고 뒤로 밀려 어쩔수 없음..

                scout_del_id = re.findall('"id":(\d+),', html_source)

                

                # 편지함에 저장된 정찰정보의 해당 좌표(정찰이 성공한 좌표만)별 ID값 추출

                if len(scout_del_id):

                    # 제대로 검출 되면!!

                    for list_item in scout_del_id:

                        print('검출된 ID : ' + list_item)

                        point_x = re.search('{"id":' + list_item + ',.+?"dx":(\d+),"dy":(\d+),', scout_info_dat).group(1)

                        point_y = re.search('{"id":' + list_item + ',.+?"dx":(\d+),"dy":(\d+),', scout_info_dat).group(2)

                        print('point_x : ' + point_x + ', point_y : ' + point_y)

                        scout_detail_url = '/game/war_result_info_api.php?jsonpcallback=jsonp' + get_time() + '&_=' + get_time() + '&key=' + base_token + '&id=' + str(list_item) + '&_l=kr&_p=SG-IPHONE-KR{}HTTP/1.1'.format(urllib.parse.quote(' '))

                        html_source = get_html_response(scout_detail_url, 2)

                        if html_source == '::ERROR::':

                            return '::ERROR::'

                        if '"code":0' in html_source:

                            str_token = str(html_source)

                            if '\\uc0b0\\ub3c4\\uc801' in str_token:

                                san_num = '1'

                            else:

                                san_num = '0'

                            if '\\ud654\\uc801' in str_token:

                                hwa_num = '1'

                            else:

                                hwa_num = '0'

                            write_str = '[' + point_x + ',' + point_y + ',' + '산도적(' + san_num + '),화적(' + hwa_num + ')]' 

                            print(write_str)

                            f_new.write(write_str + '\n')

                            rand_timesleep()

                            if int(hwa_num) == 0 and int(san_num) > 0:

                                add_friend_url = '/game/api_fav.php?jsonpcallback=jsonp' + get_time() + '&_=' + get_time() + '&key=' + base_token + '&act=addreport&wid=' + str(list_item) + '&cat=2&_l=kr&_p=SG-IPHONE-KR{}HTTP/1.1'.format(urllib.parse.quote(' '))

                                html_source = get_html_response(add_friend_url, 2)

                                if html_source == '::ERROR::':

                                    return '::ERROR::'

                                if '"code":0' in html_source:

                                    print(write_str + 'Only 산도적 오랑캐 ==> 친구추가완료!!')

                                else:

                                    print(write_str + 'Only 산도적 오랑캐 ==> 친구추가실패!!')

                                    print('add_friend_url : ' + html_source)

                                rand_timesleep()

                        else:

                            print('scout_detail_url Error : ' + html_source)

                else:

                    print('[' + point_x + '/' + point_y + '] 병력상세정보 검출 실패!!')

                    print('scout_detail_url : ' + scout_detail_url)


                if len(scout_del_id):

                    del_str = ''

                    del_id_cnt = len(scout_del_id)

                    while len(scout_del_id):

                        del_pop_item = str(scout_del_id.pop())

                        if len(scout_del_id) == 0:

                            del_str += del_pop_item

                        else:

                            del_str += del_pop_item + '%2C'

                    scout_del_url = '/game/war_result_list_api.php?jsonpcallback=jsonp' + get_time() + '&_=' + get_time() + '&key=' + base_token + '&action=delete&id=' + del_str + '&_l=kr&_p=SG-IPHONE-KR{}HTTP/1.1'.format(urllib.parse.quote(' '))

                    #print('scout_del_url : ' + scout_del_url)

                    html_source = get_html_response(scout_del_url, 2)

                    if html_source == '::ERROR::':

                        return '::ERROR::'

                    rand_timesleep()

                    if '"code":0' in html_source:

                        print('정찰완료 정보' + str(del_id_cnt) + '개 삭제 완료!!')

                    else:

                        print('정찰완료 정보' + str(del_id_cnt) + '개 삭제 실패!!')

                        print('scout_del_url : ' + scout_del_url)

                    print('다음 정찰결과 정보 추출..')

                else:

                    print('모든 정찰결과 정보 추출 완료!!')

                    break

            else:

                print('정찰결과 리스트를 불러오는데 실패하였습니다. 프로그램을 종료합니다!!')

                print('Error Code : ' + html_source)

                return '::ERROR::'


    finally:

        print('정찰결과 분석 정보가 ''orang_final.dat''에 저장되었습니다!!')

        f_new.close()


# 메인함수 시작!!


# 장소 인증

chk_auth()


print("""

***************************************************************

손바닥삼국지 도우미 Ver 0.31(alpha) - by hElLoOnG(2012.04.02)

***************************************************************

*주의사항

*이 프로그램 사용으로 인하여 발생하는 불이익에 대하여

*개발자는 어떠한 책임도 지지 않습니다.

*

*기타 문의 및 버그 수정 요청은 살포시 넣어둬 주세요 ㅋㅋ 

***************************************************************

""")


# 쿠키 생성

base_cookie = make_cookie()

print('Session 생성 : ' + base_cookie)


# 사용자 아이디/패스워드 입력부(입력안하면 기본 아이디로 진행)

temp_user_id = input('손바닥삼국지 ID : ')

if str(temp_user_id).strip() != '':

    base_user_id = temp_user_id

    print('입력된 사용자 ID : ' + base_user_id)

else:

    print('ID가 입력되지 않았습니다!!')

    sys.exit()

temp_user_pw = input('손바닥삼국지 PW : ')

if str(temp_user_pw).strip() != '':

    base_user_pw = temp_user_pw

    print('입력된 사용자 PW : ' + base_user_pw)

else:

    print('PW가 입력되지 않았습니다!!')

    sys.exit()


# 실제 앱에서 일어나는 의미없는 체크

print('손바닥 삼국지 서버로 접속을 시도합니다...')

html_source = attempt_login()

if html_source == '::ERROR::':

    sys.exit()


rand_timesleep()

    

# 사용자 서버 정보 추출

print('사용자의 손바닥 삼국지 서버 정보를 추출합니다...')

get_server_url =  '/info.php?jsonpcallback=jsonp' + get_time() + '&_=' + get_time() + '&user=' + base_user_id + '&action=login&pvp=0&code=a1c1ef3363ae6f52d8e823ecd7d62da618a98c43&_l=kr&_p=SG-IPHONE-KR{}HTTP/1.1'.format(urllib.parse.quote(' '))

html_source = get_html_response(get_server_url, 1)

if html_source == '::ERROR::':

    sys.exit()

if '"code":0' in html_source:

    base_user_host = re.search('k(\d+)\.tapsg\.com', html_source).group()

    print('사용자 서버 추출 성공 : ' + base_user_host)

else:

    print('사용자 서버정보 추출에 실패하였습니다!!\nID, PW를 확인하고 다시 시도하여 주세요!!')

    print('Error Code : ' + html_source)

    sys.exit()


# 실제 인증 키값 추출

print('손바닥 삼국지 인증키 값을 추출합니다...')

login_url = '/game/login_api.php?jsonpcallback=jsonp' + get_time() + '&_=' + get_time() + '&username=' + base_user_id + '&password=' + base_user_pw + '&_l=kr&_p=SG-IPHONE-KR{}HTTP/1.1'.format(urllib.parse.quote(' '))

print('login_url : ' + login_url)

html_source = get_html_response(login_url, 2)

if html_source == '::ERROR::':

    sys.exit()

if '"code":0' in html_source:

    base_token = re.search('key":"(\\w+)"}',html_source).group(1)

    print('사용자 인증키 추출 성공 : ' + base_token)

else:

    print('사용자 인증키 추출에 실패하였습니다!!')

    print('Error Code : ' + html_source)

    sys.exit()


# 사용자 정보 추출

#userinfo_url : jsonp1333982142599({"code":0,"ret":{"user":{"id":20440,"nick":"helloong","nationid":1,"level":39,"money":100,"guild":"\uace0\ud55c\uc74d","guildid":13,"gpower":5,"gflag":64,"protection":0,"p_end":1332411629,"status":0,"city":[{"id":23764,"name":"\ub69d\ub531\uc131","landtype":5,"x":264,"y":133},{"id":24410,"name":"\ub69d\ub531\uc1312","landtype":5,"x":265,"y":133}],"conq":[0,0,null,5],"gift":[],"pvp":0},"events":[{"id":1,"icon":"gem.jpg","name":"\uc131\uc2e4\ud55c \ub2f9\uc2e0\uc744 \uc704\ud55c \ubcf4\uc0c1! [5\/7\uc77c]","desc":"<b>\uc77c\uc77c \uc120\ubb3c<\/b>\uc740 \ub85c\uadf8\uc778 \ud6c4 \ubc1b\uc73c\uc2e4 \uc218 \uc788\uc2b5\ub2c8\ub2e4. 7\uc77c\uac04 \uc5f0\uc18d \ub85c\uadf8\uc778\uc744 \ud558\uc2dc\uba74 <b>\ub3d9\uc6d0\ub839(7\uc77c)<\/b>\uc744 \ub4dc\ub9bd\ub2c8\ub2e4!"},{"id":2,"icon":"0.png","name":"\ub4f1\uae09\uaca9\ucc28 \ubcf4\ud638\uc0c1\ud0dc","desc":"\uba3c\uc800 \uacf5\uaca9\ud558\uc9c0 \uc54a\ub294 \uc774\uc0c1, 10\ub4f1\uae09\uc774\uc0c1\uc758 \uc720\uc800\ub85c\ubd80\ud130 \ubcf4\ud638 \ubc1b\uc2b5\ub2c8\ub2e4. \uc774 \ubcf4\ud638\ub294 \ub85c\uadf8\uc544\uc6c3\ud6c4 24\uc2dc\uac04\uc774 \uc9c0\ub098\uba74 \uc790\ub3d9\uc73c\ub85c \ucde8\uc18c\ub429\ub2c8\ub2e4."}],"status":{"invite":1,"ver":0.9,"vs":1.25,"vr":0.5,"ce":1,"he":1}}})

print('사용자 정보 추출')

userinfo_url = '/game/get_userinfo_api.php?jsonpcallback=jsonp' + get_time() + '&_=' + get_time() + '&key=' + base_token + '&_l=kr&_p=SG-IPHONE-KR{}HTTP/1.1'.format(urllib.parse.quote(' '))

html_source = get_html_response(userinfo_url, 2)

if html_source == '::ERROR::':

    sys.exit()

if '"code":0' in html_source:

    base_city_id = re.search('"city":\[\{"id":(\d+),"name":',html_source).group(1)

    city_id_all  = re.findall('"id":(\d+),"name"', html_source)

    print('사용자 본성 ID : ' + base_city_id)

    print('사용자 전체성 ID : ', end ='')

    print(city_id_all)

else:

    print('사용자 정보 추출에 실패하였습니다!!')

    print('Error Code : ' + html_source)

    sys.exit()


# 사용자 테스크 정보

usertask_url = '/game/system_task_api.php?jsonpcallback=jsonp' + get_time() + '&_=' + get_time() + '&key=' + base_token + '&action=task_list&_l=kr&_p=SG-IPHONE-KR{}HTTP/1.1'.format(urllib.parse.quote(' '))

html_source = get_html_response(usertask_url, 2)

if html_source == '::ERROR::':

    sys.exit()


# 도시정보 호출

city_resource = get_city_resource(base_city_id)

if city_resource == '::ERROR::':

    sys.exit()


# cd 정보??

cdinfo_url = '/game/get_cdinfo_api.php?jsonpcallback=jsonp' + get_time() + '&_=' + get_time() + '&key=' + base_token + '&city=' + base_city_id + '&_l=kr&_p=SG-IPHONE-KR{}HTTP/1.1'.format(urllib.parse.quote(' '))

html_source = get_html_response(cdinfo_url, 2)

if html_source == '::ERROR::':

    sys.exit()


# 사용자 희망 작업 선택!!

print("""

***************************************************************

* 메뉴 선택

***************************************************************

* 1: 오랑캐 좌표 및 현시간 미점령 식량창고(대) 좌표 스캔!!

*    본성에 척후병이 약 100명정도 보유 하셔야 합니다!!

*    초반 성별 식량은 15만 이상 맞춰 주세요!!

*

* 2: ID 정찰결과 함에 존재하는 병력정보 검색(Only산도적 좌표 자동친구추가)

* 3: 도시별 연무장 소문 수집 작업(연무장 레벨 최소 16이상, 고용 공간 필요)

* 4: 친구추가 되어있는 오랑캐 자동사냥

* 5: 종료

***************************************************************


""")


which_way = int(input('원하시는 작업을 선택하여주세요[1 - 4] : '))


if which_way == 1:

    # 오랑캐 추출 갯수 입력부

    base_find_cnt = int(input('얼마나 많은 오랑캐 좌표를 찾길 원하세요?(1-' + str(base_max_cnt) + ') : '))

    if (base_find_cnt < 1) or (base_find_cnt > base_max_cnt):

        print('입력값의 범위가 잘못되었습니다.(입력값은 숫자 1 부터 ' + str(base_max_cnt) + '사이 값이어야 합니다.')

        sys.exit()

    base_find_type = int(input('어떤 종류의 오랑캐를 찾고 싶으세요(1-6)??\n(1:별6개 오랑캐,2:별5개 오랑캐,3:별4개 오랑캐, ...): '))

    if (base_find_type < 1) or (base_find_type > 6):

        print('입력값의 범위가 잘못되었습니다!!(입력값은 숫자 1부터 6사이 값이어야 합니다!!')

        sys.exit()

    point_x = int(input('지도상 x축 스캔시작 좌표 입력[4 - 270](기본값 4) : '))

    if (point_x < 4) or (point_x > 270):

        print('입력값의 범위가 잘못되었습니다!!(입력값은 숫자 4부터 270사이 값이어야 합니다!!')

        sys.exit()

    point_y = int(input('지도상 y축 스캔시작 좌표 입력[4 - 270](기본값 4) : '))

    if (point_y < 4) or (point_y > 270):

        print('입력값의 범위가 잘못되었습니다!!(입력값은 숫자 4부터 270사이 값이어야 합니다!!')

        sys.exit()

    # 지도 스캔 및 오랑캐/식량창고(대) 좌표추출

    print('지도 스캔작업을 시작합니다...')

    ret_val = scan_area_all(base_find_cnt,base_find_type,point_x,point_y)

    if ret_val == '::ERROR::':

        sys.exit()

elif which_way == 2:

    print('입력하신 ID 정찰결과 함으로 부터 병력정보 및 친구추가 작업을 진행합니다...')

    ret_str = get_enemy_info_from_file()

elif which_way == 3:

    print('다음 도시의 연무장에 1시간 5분마다 모든 도시의 한잔하기를 시행합니다!!')

    print('실행중 서버가 불안정 하거나 한잔하기에 필요한 동전이 부족하면 자동 종료됩니다!!')

    print('대상도시 ID : ', end=''); print(city_id_all)

    #GET /game/gen_conscribe_api.php?jsonpcallback=jsonp1333983704456&_=1333983724728&key=c9808b7af18f45e2e6e599ef6a0fcc02&city=23764&_l=kr&_p=SG-IPHONE-KR HTTP/1.1

    #chk_somedrink_url : jsonp1333985951179({"code":0,"ret":{"price":66,"type":3}})

    #GET /game/gen_conscribe_api.php?jsonpcallback=jsonp1333983704457&_=1333983726653&key=c9808b7af18f45e2e6e599ef6a0fcc02&city=23764&action=pub_process&_l=kr&_p=SG-IPHONE-KR HTTP/1.1

    #buy_response : jsonp1334004741746({"code":0,"ret":{"gold":102706,"price":8545,"refresh":3600,"hero":{"gid":205,"p":21,"i":8,"c1":11,"g":3,"c2":300},"rumor":0}})

    #hero gid:아이디, p:공격력, i:지혜력, c1:방어력, c2: 통솔력


    int_drink_tick = 0

    int_mod_sec = 3780 # 1시간 3분


    try:

        f_drink_name = 'drink_log_' + time.strftime('%y%m%d%H%M') + '.dat'

        while True:

            if (int_drink_tick == 0) or (int_drink_tick % int_mod_sec == 0):

                file_drink = open(f_drink_name, 'a')

                for city_id_item in city_id_all:

                    print('현재시간 : ' + time.strftime('%Y-%m-%d %H:%M:%S'))

                    chk_somedrink_url = '/game/gen_conscribe_api.php?jsonpcallback=jsonp' + get_time() + '&_=' + get_time() + '&key=' + base_token + '&city=' + city_id_item + '&_l=kr&_p=SG-IPHONE-KR{}HTTP/1.1'.format(urllib.parse.quote(' '))

                    print('chk_somedrink_url : ' + chk_somedrink_url)

                    html_source = get_html_response(chk_somedrink_url, 2)

                    file_drink.write('chk_somedrink_url : ' + chk_somedrink_url + '\n')

                    if html_source == '::ERROR::':

                        sys.exit()

                    if '"code":0' in html_source:

                        if '"refresh":' in html_source:

                            need_refresh_t = int(re.search('"refresh":(\d+),"hero"', html_source).group(1))

                            print('도시[' + city_id_item + ']의 한잔하기 남은 대기시간 : ' + str(need_refresh_t) + '초 입니다.')

                        else:

                            need_refresh_t = 0

                        need_money = re.search('"price":(\d+),"type"', html_source).group(1)

                        file_drink.write('OK[chk] : ' + str(html_source) + '\n')

                    else:

                        print('도시[' + city_id_item + ']의 소문모으기 준비 작업에 실패하였습니다!!')

                        print('Error Code : ' + html_source)

                        file_drink.write('Err[chk] : ' + str(html_source) + '\n')

                    

                    if need_refresh_t == 0:

                        get_city_money = get_city_resource(city_id_item)

                        print('remain money : ' + get_city_money[0][0] + ', need money : ' + need_money)

                        if int(need_money) > int(get_city_money[0][0]):

                            print('한잔하기에 필요한 동전이 부족하여 작업을 종료합니다!!')

                            sys.exit()

                         

                        buy_somedrink_url = '/game/gen_conscribe_api.php?jsonpcallback=jsonp' + get_time() + '&_=' + get_time() + '&key=' + base_token + '&city=' + city_id_item + '&action=pub_process&_l=kr&_p=SG-IPHONE-KR{}HTTP/1.1'.format(urllib.parse.quote(' '))

                        print('buy_somedrink_url : ' + buy_somedrink_url)

                        html_source = get_html_response(buy_somedrink_url, 2)

                        file_drink.write('buy_somedrink_url : ' + buy_somedrink_url + '\n')

                        if html_source == '::ERROR::':

                            sys.exit()

                        if '"code":0' in html_source:

                            print('buy_response : ' + html_source)

                            file_drink.write('OK[buy] : ' + html_source + '\n')

                        else:

                            print('도시[' + city_id_item + ']의 소문모으기 준비 작업에 실패하였습니다!!')

                            print('Error Code : ' + html_source)

                            file_drink.write('Err[chk] : ' + str(html_source) + '\n')

    

                int_drink_tick = 0

                int_drink_tick += 1

                

                time.sleep(1)

                file_drink.close()

            else:

                #print('현재시간 : ' + time.strftime('%Y-%m-%d %H:%M:%S'))

                int_drink_tick += 1

                #print('남은대기 초 : ' + str(int_drink_tick) + '/' + str(int_mod_sec))

                time.sleep(1)

    finally:

        file_drink.close()

elif which_way == 110:

    while True:

        print('사용자 인증키 : ' + base_token)

        print('현재시간_1 : ' + get_time())

        print('현재시간_2 : ' + get_time())

        print('사용자 본성 ID : ' + base_city_id)

        print('사용자 전체성 ID : ', end ='')

        print(city_id_all)

        input_send_str = str(input('send_str(quit is "q") : '))

        if len(input_send_str) > 1:

            input_send_str = input_send_str.format(urllib.parse.quote(' '))

        if input_send_str == 'q':

            break

        html_source = get_html_response(input_send_str, 2)

        if html_source == '::ERROR::':

            sys.exit()

        print('Response : ')

        print(html_source)

    print('테스트 종료!!')

elif which_way == 4:

    

    city_id_loop = ''

    

    # 질문1

    # 오랑캐 타입!! 어떤 오랑캘 잡을지!!

    type_orang = str(input('친구추가된 오랑캐중 어떤 종류의 오랑캐를 공격하고 싶으세요(1-6)??\n(1:별6개, 2:별5개, 3:별4개, 4:별3개, 5:별2개, 6:별1개): '))

    if (type_orang < '1') or (type_orang > '6'):

        print('입력값의 범위가 잘못되었습니다.(입력값은 숫자 1 부터 6사이 값 이어야 합니다.')

        sys.exit()

    # 질문2

    # 공격 병력타입(중보 : 11, 친위 : 15)

    type_soldier = str(input('어떤 병력으로 오랑캐를 공격하시겠습니까??\n(11: 중보병, 15: 친위기병): '))

    if (type_soldier != '11') and (type_soldier != '15'):

        print('입력값의 범위가 잘못되었습니다.(입력값은 11 또는 15 이어야 합니다.')

        sys.exit()

    # 질문3

    # 공격 병력수 100단위로 입력!!(6성 평균 기준 : 중보 : 800, 친위 : 500)

    num_soldier = int(input('몇명의 병력을 공격에 동원하고 싶으세요\n(100단위 입력, 최소300-최대800): '))

    if (num_soldier < 300) or (num_soldier > 800):

        print('입력값의 범위가 잘못되었습니다!!(입력값은 숫자 300부터 800사이 값이어야 합니다!!')

        sys.exit()

    if (num_soldier % 100) != 0:

        print('입력값의 범위가 잘못되었습니다!!(입력값은 100단위로 이루어져야 합니다!!')

        sys.exit()

    

    city_id_loop = copy.deepcopy(city_id_all)


    while city_id_loop:

        # 리스트 마지막 item을 검출!!

        last_city_id = city_id_loop[len(city_id_loop) - 1]

        # 기본대기시간  10분 60초 * 10분 = 600초

        ret_max_timesleep = 600

        

        for idx_city_id in city_id_loop:

            

            print('[' + idx_city_id + ']성의 자동사냥을 시작합니다...')

            

            ret_max_timesleep = auto_attack(idx_city_id, ret_max_timesleep, type_orang, type_soldier, num_soldier)

            # 리턴값 판별!!

            if ret_max_timesleep < 0:

                # 해당 성 자동 사냥 종료

                city_id_loop.pop(city_id_loop.index(idx_city_id))

                print('[' + idx_city_id + ']성은 자동사냥 목록에서 제외됩니다.')

            else:

                if idx_city_id == last_city_id:

                    print('자동사냥 목록에 있는 모든 성의 자동 사냥 턴이 완료 되었습니다!!')

                    print('인터벌 대기 후 재시작 합니다!!')

                    timesleep(300)

                else:

                    print('[' + idx_city_id + ']성의 자동사냥 턴이 완료 되었습니다!!')

                    print('다음성[' + city_id_loop[city_id_loop.index(idx_city_id) + 1] + ']의 자동사냥을 시작합니다!!')

                    rand_timesleep()

    print('자동 사냥 목록에 남은 성이 없습니다!!')

    input('아무키나 누르시면 자동사냥을 종료합니다.')

    sys.exit()


    # 12. 동전 동괴화 작업!!

    #GET /game/get_userinfo_api.php?jsonpcallback=jsonp1334481191259&_=1334481287964&key=a79a44877dece79457f4e78152c3b08f&action=exp&_l=kr&_p=SG-IPHONE-KR HTTP/1.1

    #GET /game/get_userinfo_api.php?jsonpcallback=jsonp1334481191260&_=1334481290297&key=a79a44877dece79457f4e78152c3b08f&action=g_cd&_l=kr&_p=SG-IPHONE-KR HTTP/1.1

    #GET /game/gold_local_market_api.php?jsonpcallback=jsonp1334481191261&_=1334481299554&key=a79a44877dece79457f4e78152c3b08f&city=23764&type=2&num=1&_l=kr&_p=SG-IPHONE-KR HTTP/1.1


elif which_way == 5:

    print('손바닥삼국지 도우미를 종료합니다.')

    sys.exit()


'Study > python' 카테고리의 다른 글

wxpython webview test  (0) 2013.10.05
[연습중]MK RSS 파싱  (0) 2013.09.23
[연습]Python regular expression & sqlite  (0) 2013.09.22
[펌]Unicode In Python, Completely Demystified  (0) 2013.09.18
python ODBC 연결시~  (0) 2013.01.26
Posted by 땡보
2013. 9. 22. 15:45

바람도 살랑 살랑 불고...

머리는 계속 썩어가고 ㅋㅋ

오늘한 학습들 끄적거리기

#!/usr/bin/env python

#-*- coding:utf-8 -*-

'''

    목  적 : Python 정규식 및 sqlite DB 연습

    버  전 : Python 2.7.5

    연습일 : 2013.09.22

    동  작 :

    나눔로또 페이지의 당첨번호 확인 페이지를 기반으로

    모든 회차의 당첨정보를 수집하여 DB파일에 저장한다.

'''


import sqlite3

import os

import re

import urllib2

import sys


class Encode:

    def __init__(self, stdout, enc):

        self.stdout = stdout

        self.encoding = enc

    def write(self, s):

        self.stdout.write(s.encode(self.encoding))


sys.stdout = Encode(sys.stdout, 'utf-8')


def GetHtmlSrc(as_url, as_decode):

    return urllib2.urlopen(as_url).read().decode(as_decode, 'ignore')


def CreateDB(as_dbfilenm):

    if os.path.exists(as_dbfilenm):

        os.remove(as_dbfilenm)


    ls_ddc = u''' CREATE TABLE LOTTO (seq int primary key not null,

                                    num1 int not null,

                                    num2 int not null,

                                    num3 int not null,

                                    num4 int not null,

                                    num5 int not null,

                                    num6 int not null,

                                    winner_cnt int null,

                                    winnings_amt int null,

                                    autowin int null,

                                    manualwin int null,

                                    url_broad varchar(255) null,

                                    url_winning_store varchar(255) null,

                                    regdate datetime default current_timestamp null,

                                    regemp varchar(10) null);  '''

    ret_val = ExecuteSql(as_dbfilenm, u'C', ls_ddc)

    if type(ret_val) == int and ret_val < 0:

        print u'DB 생성에 실패하였습니다!!'

        return -1

    return ret_val


def ExecuteSql(as_dbfilenm, as_sqltype, as_sqlquery):


    if as_sqltype <> u'C' and not os.path.exists(as_dbfilenm):

        print as_dbfilenm + u' 파일이 존재하지 않습니다.'

        return -1


    if as_sqltype == u'C' and os.path.exists(as_dbfilenm):

        print as_dbfilenm + u' 파일이 이미 존재합니다.'

        return 0


    try:

        conn = sqlite3.connect(as_dbfilenm)

        cur = conn.cursor()


        if as_sqltype <> u'S':

            conn.execute(as_sqlquery)

            conn.commit()

            return 0

        else:

            cur.execute(as_sqlquery)

            return cur.fetchall()

    except sqlite3.Error, e:

        print u'Error %s:' % e.args[0]

        if conn:

            conn.rollback()

        return -1

    finally:

        if conn:

            conn.close()


def GetLottoData(al_max_seq, as_dbfilenm):

    ll_page = 1

    while 1:

        list_result = u''

        ls_url = u'http://www.645lotto.net/Confirm/win_all.asp?sGameNo=&amp;eGameNo=&amp;sltPeriod=&amp;sltPeriod2=&page=' + str(ll_page).decode('utf-8', 'ignore')

        print u'URL : ' + ls_url

        html_src = GetHtmlSrc(ls_url, 'euc-kr')

        pattern = u'<tr>\s*?<td class=\"a\"><a href=\"/Confirm/number.asp\?sltSeq=[0-9]+?\">([0-9]+?)</a></td>\s*?<td>([0-9, ]+?)</td>\s*?<td>([0-9]*?)</td>\s*?<td class=\"right\">([0-9,]+?)</td>\s*?<td>([0-9]+?)</td>\s*?<td>([0-9]+?)</td>\s*?<td><a href=\"(.*?)\">[<img src=\"/images/Confirm/movie.jpg\" alt=\"\" style=\"cursor:pointer;\">|\s]*?</a>\s*?</td>\s*?<td class=\"a\"><a href=\"(.*?)\">바로가기</a></td>'

        re_comp_obj = re.compile(pattern)

        list_result = re_comp_obj.findall(html_src, re.DOTALL)


        for i in range(len(list_result)):

            list_result[i] = list(list_result[i])

            list_result[i][0] = int(list_result[i][0])                          #회차

            list_result[i][1] = list_result[i][1].split(u', ')                 #당첨번호

            list_result[i][2] = int(list_result[i][2])                          #일등당첨자수

            list_result[i][3] = int(list_result[i][3].replace(u',',u''))       #당첨금

            list_result[i][4] = int(list_result[i][4])                          #자동

            list_result[i][5] = int(list_result[i][5])                          #수동

            list_result[i][6] = u'http://www.645lotto.net/' + list_result[i][6].replace(u'../', u'') #당첨방송다시보기 주소

            list_result[i][7] = u'http://www.645lotto.net' + list_result[i][7] #일등판매점

            for j in range(len(list_result[i][1])):

                list_result[i][1][j] = int(list_result[i][1][j])

            print list_result[i]


            if list_result[i][0] == al_max_seq:

                print u'모든페이지 탐색 및 데이터 수집 완료!!', u'프로그램을 종료합니다.'

                exit(0)


            ls_insert_query = u'INSERT INTO LOTTO (seq, num1, num2, num3, num4, num5, num6, winner_cnt, winnings_amt, autowin, manualwin, url_broad, url_winning_store, regemp) VALUES ( '


            ls_insert_value = u''

            ls_insert_value = ls_insert_value + unicode(list_result[i][0]) + u', '

            for j in range(len(list_result[i][1])):

                ls_insert_value = ls_insert_value + unicode(list_result[i][1][j]) + u', '

            ls_insert_value = ls_insert_value + unicode(list_result[i][2]) + u', '

            ls_insert_value = ls_insert_value + unicode(list_result[i][3]) + u', '

            ls_insert_value = ls_insert_value + unicode(list_result[i][4]) + u', '

            ls_insert_value = ls_insert_value + unicode(list_result[i][5]) + u', '

            ls_insert_value = ls_insert_value + u'\'' + unicode(list_result[i][6]) + u'\', '

            ls_insert_value = ls_insert_value + u'\'' + unicode(list_result[i][7]) + u'\', '

            ls_insert_value = ls_insert_value + u'\'AUTO\'' + u' '


            ls_insert_query = ls_insert_query + ls_insert_value + u' ); '


            print u'INSERT QUERY : ' + ls_insert_query


            ret_val = ExecuteSql(as_dbfilenm, u'I', ls_insert_query)

            if ret_val <> 0:

                print u'DB Insert 실패!!'

                return -1


            if list_result[i][0] == al_max_seq:

                print u'모든페이지 탐색 및 데이터 수집 완료!!', u'프로그램을 종료합니다.'

                exit(0)

        ll_page = int(ll_page) + 1

        print str(ll_page).decode('utf-8','ignore')


def main():

    ls_dbfilenm = u'test.db'

    ls_sql = u'select max(seq) from LOTTO'

    ret_cur = ExecuteSql(ls_dbfilenm, u'S', ls_sql)

    if type(ret_cur) == int and ret_cur < 0:

        print u'DB 조회에 실패 하였습니다!'

        print u'DB 데이터를 재생성합니다!'

        ret_val = CreateDB(ls_dbfilenm)

        if ret_val <> 0:

            print u'DB 생성에 실패 하였습니다', u'프로그램을 종료합니다!!'

        ret_val = GetLottoData(1, ls_dbfilenm)


    if type(ret_cur) == list and u'None' in unicode(ret_cur[0][0]):

        print u'데이터가 없습니다!', u'데이터를 재수집합니다.'

        ret_val = GetLottoData(1, ls_dbfilenm)


    print unicode(ret_cur[0][0]) + u'회차 이후의 데이터를 수집합니다.'

    ret_val = GetLottoData(ret_cur[0][0], ls_dbfilenm)


    print u'종료!!'


if __name__ == '__main__':

    main()



'Study > python' 카테고리의 다른 글

[연습중]MK RSS 파싱  (0) 2013.09.23
[연습]손바닥삼국지 오토  (0) 2013.09.22
[펌]Unicode In Python, Completely Demystified  (0) 2013.09.18
python ODBC 연결시~  (0) 2013.01.26
Encoding type table  (0) 2012.12.27
Posted by 땡보
2013. 9. 18. 05:51

원문출처 : http://farmdev.com/talks/unicode/


Unicode in python Completely demystified.pdf


'Study > python' 카테고리의 다른 글

[연습]손바닥삼국지 오토  (0) 2013.09.22
[연습]Python regular expression & sqlite  (0) 2013.09.22
python ODBC 연결시~  (0) 2013.01.26
Encoding type table  (0) 2012.12.27
손삼 마물단계  (0) 2012.04.04
Posted by 땡보
2013. 9. 12. 04:52

원문출처 : http://blog.daum.net/maleny/89


최근에 인터넷을 배회하다가 저가의 타블렛 PC 하나를 발견하고 앱 개발 테스트용으로 사용하고
다니면서 E-BOOK 이나 읽을 용도로 구입했다.

자체 데이터 통신 기능도 없고 전화기능도 없고 당연히 DMB도 안되고 GPS 도 안되지만 
KT 의 Egg 를 들고 다니니까 Wi-Fi 를 이용한 웹 서핑 등 여러가지 필요는 충족 시킬 수 있을 것이라 판단했다.

일단 인터넷 연결을 통한 여러가지 필요한 작업은 만족 스러웠고
AlphaBiz 의 Mobile Client 역활도 잘 수행한다.
다만 스마트폰의 사이즈에 맞게 앱을 만들엇기에 큰 기기에서는 화면이 영 개판 오분..

하긴 이 타블렛을 산 이유도 이 개판 오분전을 잡기 위해서 이었지만.

문제는 이 타블렛 PC 가 컴퓨터에 설치가 안된다는 것이다.
물론 USB 케이블로 연결해 외장메모리로 사용은 된다.
그러나 앱을 개발해서 탑재하고 돌릴려면 기기가 컴퓨터에 설치가 되어야 하는데..
판매처에서 드라이버를 제공하지 않는다.

아니 제공은 커녕 게시판에 문의를 해도 도통 무슨 말을 하는지 이해 조차 하지 못하니..

여태까지는 뭐 삼숑, 엘디, 쓰까이 등등 유명 브랜드들이 만든 고가의 고급 제품들이 주류를 이루고 있고
당연히 필요한 모든 드라이버나 유용한 앱들을 기본적으로 제공되고 있고 사용자 모임 같은 카페도
활성화 되어있고 개발자들도 유명 브랜드 기기를 위주로 정보를 제공하고 있으니 문제가 없겠지만

앞으로 이처럼 저가의 보급형 기기가 쏟아져 나오게 되면
이와 같은 문제가 많이 발생할 것으로 여겨진다.

개발자들이 프로그램 개발에 대해서는 빠삭하지만 하드웨어 쪽으로 들어가면 버벅거리는 경우가 다수이고
또 초보자들이 야심차게 구입해서 앱 개발을 하려고 하는데 가장 기본적인 문제가 해결이 안되면
의욕도 상실하게 되고 성질 뻗치게 되고 마음 상하고 몸 상하는 비극이 초래할 수도 있다.

사실 나도 이 문제를 해결하기 전까지는 18 이 분당 수십번 입에서 발사되고
웹사이트를 헤메고 다니다 그냥 성질 뻗쳐서 확 컴퓨터를 꺼 버리고.
판매자 사이트에 성질도 부리고.. 

결국 약간씩의 정보를 모으고 모으고 검색하고 접근해 들어가다가
영문 사이트 (게시물이 딱 하나 있드만)를 찾아냈고 해석하고 분석하고 해보고 결국에 성공했다.
성공하자 마자 그냥 컴퓨터를 확 꺼버리고 퇴근했다.

아 친절한 알파비즈는 이렇게 발견한 정보를 친절하게 강좌한다. 것도 아주 디테일 하게..

일단 안드로이드 기기에서 개발자옵션 에서 USB 가 연결되었을 경우 디버그 모드로 연결 될 수 있도록 해준다. (기본상식)
다음 컴퓨터와 USB 를 연결하면 드라이버를 설치하라고 나온다.
아무리 찾아 봐도 맞는 드라이버를 찾을 수 없다.
설치하지 않고 끝내 버린다.

그리고 제어판의 시스템 -> 하드웨어 -> 장치관리자를 보면

 

 

 이렇게 기타 장치에 Android 라고 드라이버가 설치되지 않은 상태이거나


 

 


이렇게 Android Phone 아래에 Android 라고 드라이버가 설치되지 않은 상태로 표시가 되어있다.


자 위의 어떤 경우가 되었가나 암튼 Android 기기를 선택하고 마우스 오른쪽 버튼을 눌러서 속성을 선택한다.

 

 


위와 같이 Android 등록정보 창이 뜨면 '자세히'라는 탭을 선택하고 밑의 셀렉션에서 하드웨어 ID 를 선택한다.
그러면 위와 같이 두 줄의 뭔가가 나타나게 된다.
그냥 위 상태로 열어놓고.

다음엔 워드패드나 사용하는 텍스트에디터를 실행시킨 후 안드로이드 팩키지가 설치된 폴더 밑에
Android\android-sdk\extras\google\usb-driver\android_winusb.inf 파일을 연다.

자 이 파일은 android-sdk 의 SDK Manager.exe 를 실행했을 때
Installed package 에 Google USB Driver Package, revision 3 이상이 설치되어 있어야 한다.
없으면 구글이나 여러 사이트에서 쉽게 설치할 수 있다.

자 에디터로 연 android_winusb.inf 파일을 보자

 


 위의 붉은 글씨가 중요하다.
 일단 [Goolgle.NTx86] 라는 카테고리가 있고 [Google.NTamd64] 라는 카테고리가 있다.
 앞의 것은 32비트 OS (Window 98, XP, Vista) 용 카테고리이고
 뒤의 것은 64비트 OS (Windows NT Server, Windows 7) 용 카테고리이다.
 
 그 카테고리 명 바로 밑에 위의 붉은 부분 같이 네줄을 기록하는데.

;NOTE K   : 주석으로 기기명을 넣든지 맘대로 넣으면 된다.
%SingleAdbInterface%        = USB_Install, USB\VID_18d1&PID_0003&MI_01
%CompositeAdbInterface%     = USB_Install,
 USB\VID_18d1&PID_0003&REV_9999&MI_01
%SingleBootLoaderInterface% = USB_Install, USB\VID_0BB4&PID_0FFF

%SingleAdbInterface% 항목에는 USB_Install, 뒤에 아까 제어판에서 확인했던 Android 등록정보의 
하드웨어 ID 값의 두번째 줄의 값을 기록하고
%CompositeAdbInterface% 항목에는 하드웨어 ID 값의 첫번째 줄의 값을 기록한다.
%SingleBootLoaderInterface% 는 위와 같이 기록하면 된다.

복잡하니까 원래 있었던 
;HTC Dream 밑의 세줄을 복사해서 위에 붙혀놓고 붉은색 부분만 편집해도 된다.

자 편집한 이 네줄을 또 복사해서 아래에 있는 [Google.NTamd64] 에도 붙혀놓는다.
OS 가 32이건 64이건 그냥 그렇게 한다.

그리고 저장하고 편집기를 닫고
다시 아까 제어판의 장치관리자로가서 Android 등록정보 창에 가서 일반탭을 선택하고 '드라이버 다시 설치'를 선택한다.

-> 아니오, 지금 연결 안함 -> 다음
-> 목록 또는 특정 위치에서 설치(고급) -> 다음
-> 이 위치에서 가장 적합한 드라이버 검색을 선택하고 검색할 때 다음 위치 포함에 체크한 후 찾아보기 

아까 편집한 android_iwnusb.inf 파일이 있는
Android\android-sdk\extras\google\usb-driver 폴더를 선택한다. 아래 처럼.

 


 다음을 누르면 Android Composite ADB Interface 라는 기기로 설치가 시작된다. 

 

 


 성공적으로 설치를 완료한 상태이다.
 때에 따라 이 상황에서 재 부팅을 요구하고 다시 드라이버를 설치하라고 할 수 있다.
 그러면 재부팅하고 다시 위에서 처럼 드라이버를 재 설치하면 된다.

 다시 장치관리자를 보면

 

 위와 같이 Android Phone 아래 Android Composite ADB Interface 의 기기가 설치되어 있다.

 이클립스를 열어 개발된 앱하나를 수행해 보면
 앱이 컴파일 되고 기기에 설치되면서 작동되는 것을 볼 수 있다.

 짝짝짝..   성공!!

'Study > mobile' 카테고리의 다른 글

음.. 뽀꼬빵  (0) 2013.12.22
[연습]포코팡 오토(?) POKOPANG AUTO~  (3) 2013.12.17
[android]change system date & time  (0) 2013.11.19
[Android]Monkeyrunner  (0) 2013.11.05
[펌]Synthesizing a touch event on the iPhone  (0) 2012.08.10
Posted by 땡보
2013. 9. 8. 08:28

원문출처 : http://blog.naver.com/PostView.nhn?blogId=amuggana&logNo=140165495686 


한 컴퓨터에 두개의 OS(윈도우7, XP)설치사용

 

 

 

 

이 번 포스팅 내용은 한대의 PC에 두개이상의 운영체제(윈도우XP, 윈도우7 등)를

설치하는 방법에 관한 내용입니다.

 

두 가지 방법으로 설명을 드리도록 하겠습니다.

첫번째는 하드디스크의 개수가 1개일 때, 2가지 운영체제를 설치하는 방법이고

나머지 하나는 하드디스크가 2개이상일 때의 설치법입니다.

 

개인적으로는 후자의 방법이 훨씬 간편하고 별탈없이 사용이 용이하기에

그렇게 사용하기를 권하고 싶지만, 하드디스크가 1개인 분들도 많기에 두 가지 다 소개하죠.

 

먼저, 준비물로써

2개의 윈도우(7, XP) CD/DVD 가 필요한 건 당연하겠죠?

물론, USB로도 가능하지만, 부팅시키는 방법은 그에 대한 포스팅을 찾아보시기 바랍니다.

 

 

설명드리기에 앞서 컴퓨터 공동구매이벤트에 대해 알려드리겠습니다.

PC견적문의나 저렴한 비용으로 컴퓨터를 구입할 수있는 곳을

필자에게 물으시는 분들이 많이 계셔서

몇몇 용산업체 공동주최로 PC 공구를 진행하고 있습니다.

필요하신 분들은 아래를 클릭하여 확인해 보세요.

 

용도별 컴퓨터 공동구매

 

 

1. 1개의 하드디스크(HDD)에 2개의 윈도우 설치하기

 

하드디스크의 개수가 1개인 분들의 PC에서 윈도우XP와

윈도우7 운영체제를 설치하는 법부터 알아보겠습니다.

 

전체적인 개요부터 살펴본 후 본문으로 들어가도록 하죠.

 

 1개의 하드내에서 윈도우를 여러개 설치를 한다면,

이론적으로 4개까지 설치가 가능합니다.

하지만, 실제론 2개이상 설치할 이유는 많지 않을 테죠.

 

따라서, 2개의 운영체제 즉, 일반적으로 많이 사용하는 윈도우XP와 윈도우7 설치에 중점을 두겠습니다.

중요한 것은 1개의 하드에서 2개의 윈도우를 설치하려면, 윈도우XP부터 설치를 해야 한다는 것입니다.

달리 말하면, 하위버전 윈도우를 먼저 설치하고 상위버전의 윈도우를 설치한다는 뜻이 되죠.

만약, 윈도우7 설치를 먼저 하고 윈도우XP를 설치하게 되면 윈도우7으로 부팅이 안됩니다.

물론 해결법도 있지만, 처음부터 그걸 알고 그에 맞게 설치한다면 아무 문제가 없겠죠?

설치가 끝나면 멀티부팅메뉴는 윈도우7의 부팅관리자 창으로 나타나게 되죠.

 

파티션은 3개로 나눌 것을 권장합니다.

주파티션 2개와 논리파티션1개로 구성을 하여

주파티션 2개에는 각각의 윈도우가 설치되고 나머지 논리파티션에는 빽업공간을 두는 것이죠.

그렇기에 하드디스크가 최소 250GB 이상인 분들에게 멀티OS설치를 권장합니다.

 

파티션에 대해 간략하게 얘기를 더하자면,

활성 파티션, 주파티션, 확장파티션(논리파티션) 정도만 이해를 하시면 됩니다.

활성 파티션은 부팅에 필요한 파티션, 주파티션은 운영체제를 설치하기 위한 파티션,

마지막으로 확장파티션은 데이터를 보관(빽업)하기 위한 파티션이라고 생각하시면 편하죠.

 

활성파티션은 주파티션에만 설정이 가능하며, 디스크 1개당 하나의 활성파티션만 설정 가능합니다.

따라서, 윈도우7과 XP 두개의 운영체제를 설치하지만, 부팅영역은 같은 곳을 쓴다는 걸 알 수 있겠죠?

바로 이것때문에 윈도우XP를 윈도우7보다 먼저 설치해야하는 것이죠.

하위버전인 XP는 윈7이라는 큰 그릇을 담을 능력이 안됩니다.

그렇기에 XP를 뒤에 설치하게 되었을 때, 윈도우7의 부팅체제를

XP의 것으로 바꿔버림으로써 윈도우7 부팅이 안된다는 말이 됩니다.

반면에 윈도우7은 XP를 담을 그릇이 되니까 먼저 설치된 XP의 부팅체제를

윈7으로 바꾸더라도 XP 부팅이 가능하구요.

 

지금부터 설치를 해보겠습니다.

아래의 링크된 포스팅에서 윈도우XP 설치를 진행합니다.

 

윈도우XP 설치방법

 

위의 포스팅대로 설치를 하되, 파티션 설정부분은 링크된 포스팅에서 제공한 방법이 아닌

아래의 방법을 따를 것을 미리 말씀드립니다.

 

 

XP 설치화면에서 위와 같이 파티션 설정창이 나타나면,

현재 만들어진 모든 파티션을 제거하고 새로 파티션을 만들 것입니다.

개요에서 설명드렸던 대로 주파티션 2개와 논리파티션1개로 만듭니다.

 

현재 선택된 C드라이브에서 키보드의 'D'키를 눌러서 해당파티션을 삭제합니다.

이에 앞서 중요데이터 빽업은 말할 필요가 없겠죠?


 

위 그림처럼 파티션을 지우기 위해선 다시 'L' 키를 누르라는 메세지가 나타납니다.

이전에 운영체제가 설치되었던 상황이라면, 위 화면 이전에

엔터키를 눌러야 위 화면이 나타납니다. 'L'키를 눌러주세요.

 

그림처럼 C드라이브가 삭제되어 '분할되지 않은 공간'으로 나타납니다.

계속해서 D드라이브도 같은 방법으로 삭제를 시켜 줍니다.

 

이런식으로 현재 설정된 모든 파티션을 삭제시키면

위와 같이 하드디스크전체가 '분할되지 않은 공간'으로 나타납니다.

 

이제 새로운 파티션을 나누도록 하겠습니다.

키보드의 'C'키를 누릅니다.

 

필자는 위에서 2개의 주파티션과 1개의 논리파티션을 만든다고 했습니다.

먼저 현재의 윈도우XP가 설치될 파티션의 크기를 정해줍니다.

참고로 필자의 하드디스크의 용량은 320GB이라

70GB 정도(70000)를 할당했습니다. 

 

여러분들의 하드는 하드용량에 따라 최소45000 ~ 100000 정도 입력해 주시면 됩니다.

원하는 크기를 입력 후, 엔터키를 눌러주세요.

 

C드라이브로 70G 크기의 파티션이 생성되었습니다.

계속해서 '분할되지 않은 공간'을 선택하여 'C'키를 눌러서

남아있는 용량도 파티션을 만들어 주겠습니다.

 

이번에 만들 파티션은 윈도우7이 설치될 파티션으로,

필자는 XP와 똑같이 70000을 입력하였습니다.

입력 후, 엔터키를 눌러줍니다.

 

D드라이브에도 70G 용량의 파티션이 생성된 걸 확인할 수 있습니다.

다시 '분할되지 않은 공간'을 선택하여 'C'키를 누름으로써

나머지 파티션 생성도 완료하도록 합니다.

 

여기서, 분할되지 않은 공간 중 '8MB'는 자동으로 생기는 부분이니 신경쓰지 않아도 됩니다.

 

이번이 3번째의 파티션입니다.

총 3개의 파티션을 만들 것이니 이번에는

남아있는 하드의 용량전부를 파티션크기로 할당해 줍니다.

 

그림과 같이 모든 파티션 생성이 완료되었습니다.

만들려는 파티션 3개와 분할되지 않은 공간으로 8MB가 나타나면 정상입니다.

8MB 부분이 없는 경우도 있으니 전혀 이상할 게 없습니다.

 

C드라이브에 윈도우XP, D드라이브에 윈도우7 설치를 해야 하기 때문에

현재 그림에서 C 파티션을 필히 선택 후 엔터키를 눌러써 윈도우 XP 설치를 마무리 하세요.

좀 전의 링크로 다시 돌아가서 설치하시면 되겠죠?

 

 

윈도우 설치가 끝나고 링크된 포스팅에서 각종 설정이나 드라이버 및 프로그램 설치에 관한 부분이 나오지만,

그 전에 윈도우 XP 설치가 끝나고 바탕화면이 나타나면, 위와 같이

바탕화면의 내 컴퓨터에서 마우스 우클릭을 하여 관리로 들어와서

파티션을 재 조정 후에 윈도우 XP 설치를 마무리 하도록 하세요.

 

컴퓨터 관리창이 나타난 후, 왼쪽의 메뉴에서 디스크 관리를 클릭하면

위 그림처럼 현재 파티션이 설정된 상태를 명확하게 알 수 있습니다.

 

XP 설치 시디를 넣고 파티션을 나눈 거 기억나시죠?

보시다시피 주파티션 1개와 확장파티션 2개해서 총 3개의 파티션으로 나누어져 있습니다.

 

필자가 위에서 언급했던 내용 중에 윈도우 설치는 주파티션에서만 가능하다고 말씀드렸습니다.

위 그림을 보시면 XP가 설치된 C드라이브만 주파티션이고

나머지 D와 E드라이브는 확장파티션에서 논리드라이브로 구성되어 있는 게 보입니다.

이렇게 되면, D드라이브에 윈도우7 설치가 안됩니다.

물론, 추후에 윈도우7을 설치할 때 다시 파티션을 구성할 수 있으나

그 방법보다는 현재 이 화면에서 미리 파티션을 원래 계획했던 대로 구성을 해놓고

윈도우7을 설치하는 게 훨씬 편하다는 거죠.

 

자, 그러면 파티션 조정을 해보겠습니다.

 

C드라이브는 정상적으로 되어있고 윈도우 XP가 설치되었으니 그대로 놔두고

D와 E라는 논리드라이브와 그걸 감싸고 있는 확장파티션을 삭제할 것입니다.

 

먼저, D드라이브에서 마우스 우클릭을 하여 '논리 드라이브 삭제'를 클릭합니다.

 

데이터 손실되는 건 당연하고 어차피 아무것도 없으니 '예'를 클릭합니다.

 

D드라이브가 삭제되어 해당부분이 확장파티션만 남게 되었습니다.

계속해서 E드라이브도 같은 방법으로 삭제를 시켜주세요.

 

D와 E드라이브가 삭제되면 해당부분이 확장파티션이라는 빈 껍데기만 남게 됩니다.

역시 확장파티션도 삭제를 시켜 주겠습니다.

우클릭 후 '파티션 삭제'를 클릭.

 

드디어, '할당되지 않음'으로 나타났습니다.

'새 파티션'을 클릭하여 다시 파티션을 나눠주도록 하겠습니다.

 

파티션 만들기 마법사 창이 뜨면, '다음'을 클릭하시고

파티션 형태를 정해주는 화면에서 위 그림처럼 '주 파티션'을 선택 후, '다음'을 클릭합니다.

 

현재 만들 파티션은 윈도우7이 설치될 파티션이기 때문에 주파티션으로 생성을 하는 것이죠.

 

현재 남은 공간에서 윈도우XP가 설치된 파티션크기처럼

70GB정도를 윈도우7 파티션으로 할당할 것입니다.

 

XP와 똑같이 70000이라고 입력을 하게되면,

추후에 윈도우7 설치시에 같은 크기의 파티션이 2개가 존재하므로,

실수로 XP가 설치된 파티션에 윈도우7을 설치할 우려가 있을 수 있겠죠??

 

그래서, XP의 파티션보다 약간 더 크게 필자는 71000을 입력하였습니다.

계속해서 다음을 클릭해서 나오는 창에서 아무것도 손대지 마시고 다시 '다음' 클릭.

 

그림과 같이 '볼륨 레이블'에는 공란으로 비워두시고, '빠른 포맷 실행'에 체크 후, 다음을 클릭합니다.

그리고, 마침 버튼을 눌러주세요. 

 

XP가 설치된 C드라이브와 같은 색깔(주 파티션)의 파티션이

조금 더 큰용량의 D드라이브로 나타난 게 확인되죠?

 

계속해서 '할당되지 않음'에서 남아있는 파티션을 확장파티션으로 만들어 주겠습니다.

마우스 우클릭을 하여 '새 파티션'을 클릭하세요. 

 

이번에는 주 파티션이 아닌 '확장 파티션'을 선택하고 다음을 클릭합니다.

윈도우 2개가 설치될 주파티션의 개수가 2개로 되었으니,

남은 파티션은 논리로 만들어서 데이터보관용으로 쓰기 위함입니다.

 

남아있는 하드디스크 용량 전부를 할당하여 다음을 눌러줍시다.

 

위 그림과 같이 확장파티션이 생성되었습니다.

이대로는 사용이 불가능하기 때문에 확장파티션을 논리드라이브로 만들겠습니다.

 

해당 공간에서 마우스 우클릭을 하여 '새 논리 드라이브'를 클릭.

 

뒤이어 나타나는 창은 D드라이브를 생성하는 과정과 똑같기 때문에 생략하겠습니다.

단, 용량은 남아있는 공간 전체로 할당해 주셔야 합니다.

 

드디어 파티션이 원하는대로 2개의 주파티션(C,D)과 1개의 논리파티션으로 설정 완료되었습니다.

이제는 링크페이지로 돌아가셔서 윈도우 XP 설치에 관한 모든 것을 마무리 하시기 바랍니다.

 

윈도우 XP 설치가 완전히 끝나면 윈도우7 설치 DVD를 넣고 윈도우XP화면을 종료시킵니다.

이 때, 윈도우에서 DVD를 읽어들여 윈도우7 설치화면이 나타난다면,

실행시키지말고 창을 닫고 컴퓨터를 종료합니다.

 

윈도우7 설치방법

 

XP 설치가 끝났으니 위의 링크를 통해 윈도우7을 설치합니다.

 

단, 아래의 화면처럼 파티션 설정부분이 나타나면

링크에서 설명된 부분을 따르지 말고 아래의 설명을 따라서 설정해 주시면 됩니다.

 

 

윈도우 XP를 설치하면서 파티션을 재조정하여 나눈 부분이 그대로 나타나죠?

위 그림에서 '디스크0' 이란 말은 현재 1개인 하드디스크를 말하며,

파티션 1, 2, 3 이 바로 주파티션 2개와 논리 파티션 1개를 뜻합니다.

 

자....윈도우 XP는 이미 설치가 되었고...

윈도우7은 위의 파티션 중에서 어디에 설치를 해야 할까요?

위에서 제가 드린 설명을 제대로 이해를 하셨다면, 바로 느낌이 올 것입니다.

 

'파티션1'에 윈도우 XP가 현재 설치되어 있습니다.

여기에 윈도우7을 설치하면 당연히 안되겠죠?

'파티션3' 역시 논리 드라이브라서 윈도우7 설치가 불가합니다.

그렇습니다. '파티션2'에 윈도우7을 설치할 것입니다.

용량을 봐도 쉽게 알 수 있죠? 윈도우XP의 파티션보다 약간 더 큰 용량을 찾으면 되는 거죠.

 

해당 파티션인 '파티션2'를 선택하고 '드라이브 옵션'을 클릭합니다. 

 

그림처럼 포맷을 눌러줍니다.

이미 XP상에서 파티션 및 포맷이 끝난 상태이나,

혹시 모를 불순물이 섞이지 않게 포맷을 한 번 더 해주고 설치를 하자는 거죠.

 

위와 같이 데이터가 들어있을 수가 있는 데 포맷을 해서 지울꺼냐는 메시지가 나타납니다.

어차피 윈도우7 설치를 위해 비워둔 파티션이기에 내용이 있을리가 없겠죠?

확인 버튼을 클릭하면 순식간에 포맷이 완료됩니다.

 

포맷이 완료되면, 윈도우 7을 설치하기 위해 '파티션2'가 선택된 걸 필히 확인하시고

다음 버튼을 클릭하여 윈도우 7 설치를 마무리하도록 합니다.

 

링크 페이지를 보시고 설치를 따라하시다가 XP와 마찬가지로 바탕화면이 나타나면,

아래의 설정 먼저 해 주시고 윈도우 7 설치를 마무리하세요.

 

 

바탕화면의 컴퓨터 아이콘에서 마우스 우클릭을 하여 '관리'를 클릭합니다.

그리고 위의 컴퓨터 관리 창이 나타나면, 좌측 메뉴에서 '디스크 관리'를 누릅니다.

 

윈도우 7 상에서 파티션이 어떻게 나타나는 지 확인이 되죠?

그림처럼 D드라이브가 XP가 설치된 파티션이란 걸 알 수 있겠죠?

XP에서는 C드라이브로 표기가 됩니다.

 

그리고, C드라이브가 현재 윈도우7이 설치된 파티션이고

마지막으로 E드라이브가 마지막 남은 논리 파티션입니다.

 

즉, XP와 윈7 입장에서 봤을 때....서로 C와 D만 바뀌었다는 게 됩니다.

서로의 입장(윈도우)에서 보면, 각각이 설치된 드라이브가 버젓이 노출이 된 상황이죠.

 

이렇게 되면, 현재 윈도우7을 사용하면서 추후에 빽업데이터라던지, 삭제나 추가되는 폴더가

D드라이브(윈도우 XP가 설치된 파티션)에서 이뤄질 수 있다는 걸 의미합니다.

한마디로, 잘못 건드려 윈도우XP를 못 쓰게 될 수도 있다는 거죠.

윈7이 아니라 XP입장에서도 마찬가지로 잘못 건드려 윈도우7을 못 쓰게 만들 수도 있습니다.

 

따라서, 해당 파티션은 건들 수 없도록 설정을 하겠습니다.

내 컴퓨터의 목록에서 안 보이게 설정을 한다는 뜻입니다.


 

그림과 같이 D드라이브에서 마우스 우클릭을 이용하여 '드라이브 문자 및 경로 변경'으로 들어갑니다.

 

위의 화면대로 차례대로 '제거', '예', '예'를 클릭하세요.

나타나는 문구에 겁 먹을 수도 있으나, 전혀 그럴 필요가 없습니다.

해당 드라이브의 내용을 지우는 게 아니라 윈도우7 상에서

아예 사용을 못하게 연결을 끊어 놓겠단 말입니다.

 

다시 디스크 관리 창을 보시면,

조금 전 D드라이브의 문자표시가 사라진 게 보입니다.

 

이렇게 되면, 문자가 조금 꼬이게 되죠?

C와 E드라이브에 시디롬이 F로 되어 있으니 보기가 안 좋습니다.

차례대로 C, D, E가 되게 만들어 줍시다.

 

E드라이브에서 우클릭을 하여 다시 '드라이브 문자 및 경로 변경'으로 들어갑니다.

 

조금 전에는 제거를 하였지만, 지금은 '변경'을 클릭해 주세요.

다음 화면에서 '드라이브 문자 할당'에서 문자를 'D'로 바꿔주고 확인을 누릅니다.

마지막 화면 역시 '예'를 클릭.

 

논리파티션이 D드라이브로 바뀐 게 확인되죠?

시디롬 역시 위와 같은 방법으로 E드라이브로 바꿔주시면 됩니다.

 

바탕화면의 '컴퓨터' 아이콘을 클릭하여

실제로 우리 눈에 보이는 디스크를 살펴보니 위 그림과 같이

깔끔하게 C, D, E로 표현되고 XP가 설치된 파티션은 안 보입니다.

 

여기까지 확인하셨으면 일단 재부팅을 해 봅니다.

 

 

그림과 같이 재부팅되면서 윈도우7의 부팅 관리자에서

자동으로 두가지 항목의 운영체제(윈도우 XP, 윈도우 7)가 나타나서 선택할 수 있는 메뉴가 보입니다.

기본적으로 30초 안에 선택하게끔 되어있는 데, 이 시간동안 아무것도 누르지 않게 되면

그림에서 보듯이 윈도우7에 표시가 되어있기 때문에 윈도우7으로 부팅이 되게 됩니다.

 

다 좋은 데, 두가지가 맘에 안 드는 군요.

윈도우 XP가 '이전 버전의 Windows'라고 표기되어 있고,

30초라는 인터벌이 너무 길다는 것이죠.

문구가 '윈도우 XP'로 표시되면 좀 더 알아보기 쉽겠죠?

게다가 어차피 윈도우7으로 부팅할 거라면 30초나 기다릴 필요가 없습니다.

 

따라서, 이 부분을 수정하는 작업을 하겠습니다.

표기되는 문구는 '윈도우 XP' 이고, 인터벌 시간은 5초로 바꿀 것입니다.

아래에서 설명하는 방법대로 하시되 문구나 시간은 본인이 다르게 설정하셔도 상관없습니다.

 

현재의 메뉴가 윈도우7에서 제공하는 것이므로 윈도우 7으로 부팅하여 내용을 바꿔주도록 합니다.

 

 

바탕화면의 윈도우 로고를 클릭하여 검색창에 위와 같이 'cmd' 라고 입력합니다.

위 그림처럼 'cmd'라는 프로그램이 자동으로 검색되어 나타나면,

해당 프로그램에서 우클릭 메뉴중 '관리자 권한으로 실행'을 클릭하세요.

 

검색창에서 cmd라고 입력 후, 바로 엔터를 눌러도 되지만 가끔씩 실행이 안되는 경우도 있기 때문입니다.

 

위의 명령프롬프트 창이 나타나면,

그림과 같이 'bcdedit'를 입력하고 엔터를 눌러줍니다.

 

목록에서 위의 빨간 네모부분을 찾아보세요.

'description'의 내용이 '이전 버전의 Windows'라고 되어있는 부분이 보입니다.

이 부분을 '윈도우 XP'로 바꾸겠습니다.

 

화면 맨 아래의 입력란에서 위와 같이

'bcdedit /set {ntldr} description "윈도우 XP"'라고 입력해 주신 후 엔터를 누르세요.

그리고 현재 창을 닫으시면 됩니다. 띄워쓰기 주의하세요.

 

bcdedit의 내용 중 ntldr(엔티엘디알)이라는 식별자의 문구를

""(큰따옴표)안의 문구로 설정을 하겠단 뜻입니다.

 

따라서, 윈도우 XP라는 문구대신 다른 말은 본인이 알아서 입력하시면 됩니다.

 

 

바탕화면의 컴퓨터 아이콘에서 우클릭 후, 속성으로 들어가면 위와 같이 시스템 창이 나타납니다.

좌측 메뉴 중에서 '고급 시스템 설정'을 클릭합니다.


 

위의 첫번째 그림에서 '시작 및 복구' 메뉴의 설정을 클릭하면,

두번째 그림과 같이 '운영 체제 목록을 표시할 시간'이 보입니다.

 

해당 부분의 시간을 원하는 시간으로 고쳐주시면 됩니다. 필자는 5초로 정했습니다.

다 되었으면 확인 버튼을 클릭하시고,

첫 번째 그림인 시스템 속성창도 확인을 누르면 됩니다.

 

이제 다시 재부팅을 하여 확인을 해보겠습니다.

 

 

 

문구가 바뀐 게 확인이 되죠?

시간도 30초에서 카운트다운이 아닌 5초에서 카운트다운을 시작합니다.

 

이 화면이 나타난 김에 윈도우 XP를 선택하여 부팅을 해 봅니다.

윈도우7에서 XP파티션이 안보이게 설정한 것처럼,

윈도우 XP에서도 윈도우7이 설치된 파티션이 안보이게 설정을 하기 위해서 입니다.

 

 

내 컴퓨터에서 우클릭하여 관리로 들어와서 다시 디스크 관리를 클릭하면 위와 같이 나타납니다.

윈도우7과 방법이 완전히 똑같습니다.

그림처럼 윈도우7 파티션을 제거하고 드라이브 문자를 순차적으로 수정해 주세요.

 

내 컴퓨터에서 목록을 확인해 보니 역시 깔끔하게 나옵니다.

이제는 멀티부팅으로 윈도우 XP와 윈도우 7 설정에 관한 내용이 모두 끝났으니

윈도우 7으로 다시 부팅하여 위의 링크페이지를 보시고

윈도우 7 설치를 완벽히 끝낸 후 사용하시면 됩니다.

 

 

2. 2개의 하드디스크(HDD)에 2개의 윈도우 설치하기

 

이제는 하드디스크의 개수가 물리적으로 2개일 때,

윈도우 XP와 윈도우 7 운영체제를 설치하여 멀티부팅하는 법에 대해 알아보겠습니다.

 

참고로 필자의 경우는 위의 방법이 아닌 여기서 소개하는 방법으로 다중 운영체제를 설치하여 사용중입니다.

 

개요 설명 들어갑니다.

이 방법은 굉장히 쉽습니다.

따로 설명이 필요한 것도 아니고 그냥 일반적으로 윈도우를

각각의 하드디스크에 설치만 하면 끝납니다.

윈도우 설치법은 위에서 XP와 윈도우 7 둘 다 링크를 걸어드렸으니

거기에 적힌 설명대로 따라만 하시면 됩니다.

 

단, 설치할 때의 유의사항과 어떤 운영체제로 부팅할 지 결정하는 방법만

설명드리면 무난하게 누구라도 쉽게 할 수 있는 방법이죠.

 

일단, 한 번 보도록 하죠.

 

  

 

PC 본체의 내부 사진입니다.

그림과 같이 두 개의 하드디스크가 보입니다.

 

각각의 하드에 윈도우 XP와 윈도우 7을 설치할 것입니다.

해당되는 하드디스크에 맞는 운영체제를 설치시에 나머지 하드디스크는

그림처럼 컴퓨터가 꺼진상태에서 전원선과 데이터연결선을 뽑아놓고 설치를 하시면 됩니다.

위에서는 사타하드만 나와있지만, IDE하드도 마찬가지로 전원선과 40핀짜리 연결선을 뽑으세요.

 

이렇게 하지 않고, 하드디스크마다 선이 연결된 상태에서 운영체제를 설치하게 되면,

먼저 설치된 운영체제가 추후에 설치된 운영체제에 의해 부팅 간섭으로 오류가 생겨

부팅이 되지 않는 증상이 나타날 때가 있더군요. 서로가 물리적으로 독립된 하드인데도 말이죠.

 

따라서, 간섭이 없게끔 처음부터 운영체제를 설치할 하드를 제외한

나머지 하드디스크는 아예 격리를 시켜놓고 시작하자는 말입니다.

 

위의 그림에서는 상단에 위치한 하드디스크에 먼저 운영체제를 설치할 것이므로

하단의 하드디스크는 선을 모조리 뽑았습니다.

하단의 하드디스크에 운영체제를 설치시에도 마찬가지로 상단의 하드디스크선을 모조리 뽑아야 겠죠?

 

각각의 하드디스크에 운영체제 설치가 완전히 끝났으면,

모든 하드디스크의 선을 원래대로 연결합니다. 물론 PC가 꺼진 상태에서...

 

그리고, 컴퓨터를 부팅시킨 후 위와 같은 화면이 나타났을 때,

키보드의 오른쪽 상단에 'Pause' 또는 'Break'키를 눌러서 현재 화면을 정지시킵니다.

내용에서 위의 네모부분처럼 바이오스로 진입할 수 있는 키를 확인합니다.

필자의 경우는 'Press DEL to run Setup'에서 알 수 있듯이

키보드의 'Delete'를 눌러서 진입하라고 나와있습니다.

 

각자의 컴퓨터에 맞는 키가 표시되니 적힌대로 눌러서 바이오스로 들어갑니다.

 

바이오스 창이 나타나면 위 화면에서 'boot'로 이동 후

하드디스크의 부팅순서를 정해줍니다.

 

위의 예는 아미바이오스이지만, 어워드바이오스의 경우에는

위에서 두번째 메뉴 즉, Advanced~~로 시작하는 부분으로

들어가서 찾아보시면 됩니다. 자세한 건 윈도우 설치법에도 나와 있습니다.

 

그림에서 'Hard Disk Drives' 메뉴를 선택 후, 엔터키를 누릅니다.

 

세부내용에서 위와 같이 2개의 하드디스크가 나타납니다.

이 메뉴에서는 하드디스크의 개수만큼 목록에 나타나니 참고하세요.

 

필자는 삼성하드에 윈도우 XP를 히다치하드에 윈도우 7을 설치하였습니다.

현재는 첫번째(1st)로 부팅시킬 하드가 삼성하드로 되어있는 게 확인됩니다.

 

다른말로, 컴퓨터를 켜면 윈도우 XP로 부팅된다는 뜻이죠.

사용자분들의 편의에 따라 주로 부팅할 운영체제를 결정하고

해당 운영체제가 설치될 하드디스크를 1번 순서로 바꾸는 작업을 한다는 말이 되죠.

 

기본 윈도우 7으로 부팅되게 하려면,

그림과 같이 '1st Drive' 즉, 첫번째 부팅시킬 하드디스크를 선택 후, 엔터를 누릅니다.

위의 목록이 나타나면, 항목 중에서 히다치 하드를 선택하시고 엔터를 누르면 되겠죠?

 

그림과 같이 히다치하드가 1번이 되면서

자동으로 삼성하드는 2번순서로 내려갔습니다.

 

키보드의 'F10'키를 눌러서 위의 저장메시지가 나타나면

'OK'를 선택하여 엔터키를 쳐서 해당 설정을 저장하고 빠져나갑니다.

 

이로써 현재의 PC는 전원을 켜면 윈도우7으로만 부팅이 됩니다.

 

한가지 의문이 들지 않나요?

윈도우 XP로 부팅하기 위해서는 매번 바이오스로 들어와서

하드디스크 순서를 바꿔줘야 할까요?

 

아래의 그림을 다시 한 번 봐 주세요.

 

컴퓨터 부팅시에 나타나는 문구를 잘 살펴보시면,

'Press F8 for BBS POPUP'이란 메뉴가 보입니다.

 

해당 문구대로 'F8'키를 눌러보겠습니다.

여러분들은 위 창을 멈춰놓고 보시면 진입키가 필자와는 각자 틀릴 것입니다.

대체적으로 'F9'키 또는 'F11'키를 눌러서 들어가는 경우가 일반적입니다.

어째든 각자의 컴퓨터에 나타나는 문구대로 눌러주세요.

 

'F8'키를 누르니, 위와같이 부팅장치를 고를 수 있는 팝업메뉴창이 선택되었다는 메세지가 영어로 뜹니다.

어떻게 나오는 지 봅시다.

 

아하!! 위와 같이 나타나는 군요.

CD롬과 하드디스크 2개가 목록에 바로 떳습니다.

 

여기에서 윈도우 XP가 설치된 삼성하드를 선택하여 엔터키를 치면 됩니다.

 

위의 메뉴창에서의 선택은 1회성으로 그칩니다.

즉, 추후에 컴퓨터를 다시 켜면 바이오스에서 1번으로 설정한 하드디스크인

윈도우 7으로 부팅이 된다는 뜻이죠.

 

그렇기 때문에 주로 쓰는 운영체제를 위의 바이오스상에서 1번으로 정해주고

한번씩 다른 운영체제로 부팅할 때는 위와 같이 1회성으로 선택하여 진입하면 됩니다.

다른 PC에서는 'ESC'키를 눌러야 1회성 부팅메뉴가 나오는 군요.

이해가 되셨나요?

 

어때요? 하드디스크만 여러개면

후자의 방법이 훨씬 간편하면서도 시원하죠?


Posted by 땡보
2013. 8. 21. 17:00

많이 알고 있다고 자부하는 사람.

자신이 부족하다고 느끼며 새로운 것을 배우려는 사람.

어느 쪽이 되고 싶은가?


몸이 늙는 건 숙명이지만 정신이 늙는 건 선택이다.

대개의 사람들이 조금씩 하루도 빠짐없이

신념과 용기와 꿈이 있던 자리를

회의와 비굴과 협잡으로 채워 갈 때,

그런 순수한 오염의 과정을

철이 들고 성숙해 가는 과정이라고 거대하게 담합할 때,

여전히 신념과 용기와 꿈을 좇으며 살아가는 늙은 청년들이 있다.

- 나는 왜 불온한가 中 -


세상에 대하여 더이상 회색분자가 되지 말아라.

훗날 과오를 인정하게 될 지언정,

지금은 지금의 신념과 믿음으로

나의 가치관을 정립하고 밀고 나가야 하는 것이다.

끝없이 중간에서 방황하는 자,

판단을 유보하고 행동을 유기하는 자.

너는 아무 것도 이룰 수 없을 것이다.


자기 철학이 없는 자가 흔들림 없이 걸어간다는 것은

도무지 말이 안되는 일이다.


생각이 복잡할 땐 간단하게 행동하라.

앞이 보이지 않을 땐 걸어온 길을 돌아보라.


누군가가 죄를 짓거나 타인에게 피해를 입히는 것은,

그가 못되거나 악해서가 아니라

약하고, 강하지 못하기 때문이다.

그리고 누군가가 그 사람을 미워하는 것도

약하고, 강하지 못하기 때문이다.

강한 자는

죄를 지을 이유도,

타인에게 피해를 입힐 이유도,

남을 미워할 이유도 없다.


기본적인 편견이 있으면,

상대편이 어떤 말을 해도 수긍하지 못한다.

내가 열려있으면 사람들도 열린 상태로 날 대하게 되고

닫혀있으면 사람들도 날 닫힌 상태로 대하게 된다.


살아온 세월을 무의미하지 않게 만드는 방법은

다시 일어서는 것 뿐.

환경결정론적인 사람이 되지 말자.


상대를 믿는다는건
상대가 깨끗하다는 믿음 때문이겠지.
세상이 온통 얼룩진 곳이어도
상대는 깨끗할거라는 믿음 때문이겠지.
설사 그렇지 않다는 걸 알고 있더라도
믿기로 결심했다면
그 결심을 따라서 생각하는 것일꺼다.

그래. 

너, 혹은 내가 그렇게 타인의 진심을 얻을만큼
깨끗한 사람은 아닐지도 모르지.
하지만 이렇게 믿음을 약속하였다면.
지금부터라도
더 깨끗해지도록 노력하자.
당신의 믿음이 부끄럽지 않게.


'Study > 되새김질' 카테고리의 다른 글

Sybase ASA log  (0) 2012.01.20
[펌]sed 명령어  (0) 2011.12.25
[C/C++]SBCS/MBCS/WBCS 관련 함수 참고  (0) 2011.09.08
Posted by 땡보
2013. 8. 20. 16:59

원문 : http://freeimage.sourceforge.net/

PNG to JPG

JPG to BMP

PNG to BMP

BMP to PNG

... etc

FreeImage3154Win32.zip

 

참고~

Posted by 땡보