[완료] bash 쉘 스크립트, "01"같이 0이 붙은 변수를 산술연산하려면?
로또 분석을 위해 bash shell script로 간단히 분석 프로그램을 만들고자 하였으나 각종 제약이나 알 수 없는 작동 때문에 어히려 c로 만드는 것보다 더 어려워졌습니다.
프로그램 아이디어는 다음과 같습니다.
1. 역대 로또 당첨 번호를 모두 배열에 넣는다.
2. 일정 기간 동안 나온 숫자 빈도를 deabak 배열에 저장. deabak 배열은 0~44까지의 배열로 1~45 숫자가 나오면 해당 숫자에 맞는 배열에 +1을 한다. 예를 들어 39가 나오면 deabak[38]+=1 하는 식으로.
3. deabak 배열 0~44까지를 출력. 해당 기간 동안 많이 나온 숫자, 적게 나온 숫자를 보며 대박 꿈을...
그런데 bash의 array는 이중배열도 안돼,
array[$i]=$j 이런 형태로 값을 넣는 것도 안되고
${array[$i]}=$j 이렇게 하면 명령어 실행으로 받아들이고
array=( [$i]=$j ) 이런 형태로 값을 넣어야 하더군요.
뭐 그렇긴 한데 문제는 로또 숫자를 넣은 array에 01, 02, 03...09로 저장해놓은 숫자가 문제더군요. 해당 숫자가 나오면
test.sh: line 243: 09: value too great for base (error token is "09")
이렇게 에러가 나네요.
#!/bin/bash deabak=( 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 ) array=( 10 23 29 33 37 40 16 09 13 21 25 32 42 02 11 16 19 21 27 31 30 14 27 30 31 40 42 02 16 24 29 40 41 42 03 14 15 26 27 40 42 34 02 09 16 25 26 40 42 08 19 25 34 37 39 09 02 04 16 17 36 39 14 09 25 30 33 41 44 06 01 07 36 37 41 42 14 02 11 21 25 39 45 44 22 23 25 37 38 42 26 02 06 12 31 33 40 15 03 04 16 30 31 37 13 06 07 24 37 38 40 33 03 04 09 17 32 37 01 03 12 13 19 32 35 29 06 30 38 39 40 43 26 10 14 18 20 23 30 41 06 12 17 18 31 32 21 04 05 06 08 17 39 25 05 13 17 18 33 42 44 07 08 27 29 36 43 06 02 04 21 26 43 44 16 04 05 07 18 20 25 31 01 20 26 28 37 43 27 09 18 23 25 35 37 01 01 05 13 34 39 40 11 08 17 20 35 36 44 04 07 09 18 23 28 35 32 06 14 19 25 34 44 11 04 07 32 33 40 41 09 09 26 35 37 40 42 02 02 03 11 26 37 43 39 01 10 23 26 28 40 31 07 27 30 33 35 37 42 16 17 22 30 37 43 36 06 07 13 15 21 43 08 07 13 18 19 25 26 06 13 20 23 35 38 43 34 17 18 19 21 23 32 01 06 31 35 38 39 44 01 03 11 21 30 38 45 39 01 10 20 27 33 35 17 08 13 15 23 31 38 39 14 17 26 31 36 45 27 06 10 18 26 37 38 03 04 07 16 19 33 40 30 02 10 12 15 22 44 01 02 03 11 16 26 44 35 02 04 15 16 20 29 01 07 08 14 32 33 39 42 01 08 21 27 36 39 37 17 21 31 37 40 44 07 10 14 30 31 33 37 19 07 10 16 25 29 44 06 10 24 25 33 40 44 01 06 29 36 39 41 45 13 02 08 25 36 39 42 11 14 15 19 30 38 43 08 03 08 15 27 29 35 21 03 20 23 36 38 40 05 14 15 18 21 26 36 39 04 25 33 36 40 43 39 02 03 07 17 22 24 45 03 07 10 15 36 38 33 10 12 15 16 26 39 38 05 08 14 15 19 39 35 05 19 22 25 28 43 26 05 09 12 16 29 41 21 02 04 11 17 26 27 01 03 12 18 32 40 43 38 06 15 17 18 35 40 23 02 05 24 32 34 44 28 01 03 15 22 25 37 43 02 18 29 32 43 44 37 10 13 25 29 33 35 38 03 12 24 27 30 32 14 17 18 24 25 26 30 01 05 07 11 13 20 33 06 01 02 03 14 27 42 39 06 10 15 17 19 34 14 16 23 27 34 42 45 11 06 08 13 23 31 36 21 02 12 37 39 41 45 33 04 12 16 23 34 43 26 01 17 20 24 30 41 27 04 26 28 29 33 40 37 17 20 29 35 38 44 10 01 21 24 26 29 42 27 03 14 24 33 35 36 17 06 22 24 36 38 44 19 05 32 34 40 41 45 06 08 17 27 31 34 43 14 01 03 08 21 22 31 20 06 07 14 15 20 36 03 06 09 16 23 24 32 43 01 03 10 27 29 37 11 01 07 11 23 37 42 06 01 03 17 32 35 45 08 17 22 24 26 35 40 42 05 14 15 27 30 45 10 17 32 33 34 42 44 35 08 10 20 34 41 45 28 04 10 12 22 24 33 29 01 04 05 06 09 31 17 07 18 22 23 29 44 12 01 05 34 36 42 44 33 07 20 22 23 29 43 01 07 18 31 33 36 40 27 26 29 30 33 41 42 43 04 09 28 33 36 45 26 11 14 19 26 28 41 02 01 02 06 09 25 28 31 02 04 25 31 34 37 17 05 10 22 34 36 44 35 03 04 10 17 19 22 38 03 11 13 14 17 21 38 04 06 10 11 32 37 30 12 28 30 34 38 43 09 01 11 16 17 36 40 08 07 17 18 28 30 45 27 04 16 23 25 29 42 01 02 08 32 33 35 36 18 07 20 22 27 40 43 01 03 05 10 29 32 43 35 12 30 34 36 37 45 39 19 23 25 28 38 42 17 07 19 24 27 42 45 31 08 10 11 14 15 21 37 03 17 23 34 41 45 43 04 07 15 18 23 26 13 03 12 20 23 31 35 43 06 14 22 28 35 39 16 02 16 30 36 41 42 11 07 09 20 25 36 39 15 10 11 27 28 37 39 19 09 11 15 20 28 43 13 03 13 17 18 19 28 08 08 12 29 31 42 43 02 12 16 30 34 40 44 19 26 27 28 42 43 45 08 04 15 17 26 36 37 43 02 03 13 20 27 44 09 02 19 27 35 41 42 25 04 06 13 21 40 42 36 21 25 33 34 35 36 17 02 11 21 34 41 42 27 02 18 25 28 37 39 16 01 02 10 13 18 19 15 01 05 13 26 29 34 43 03 08 11 12 13 36 33 06 19 21 35 40 45 20 16 19 20 32 33 41 04 05 18 28 30 42 45 02 19 26 30 33 35 39 37 04 09 13 18 21 34 07 01 18 30 41 42 43 32 03 07 08 34 39 41 01 22 34 36 40 42 45 44 01 05 21 25 38 41 24 07 11 26 28 29 44 16 06 09 10 11 39 41 27 05 13 18 19 22 42 31 09 12 27 36 39 45 14 24 27 28 30 36 39 04 03 10 31 40 42 43 30 16 27 35 37 43 45 19 02 11 13 15 31 42 10 04 16 25 29 34 35 01 04 19 21 24 26 41 35 03 09 24 30 33 34 18 13 14 18 22 35 39 16 19 26 28 31 33 36 17 04 17 30 32 33 34 15 01 10 13 16 37 43 06 01 05 11 12 18 23 09 05 09 17 25 39 43 32 02 15 20 21 29 34 22 14 21 23 32 40 45 44 13 15 27 29 34 40 35 02 18 24 34 40 42 05 01 02 06 16 20 33 41 01 02 04 08 19 38 14 04 10 14 19 21 45 09 01 02 08 18 29 38 42 19 24 27 30 31 34 36 08 14 32 35 37 45 28 08 14 18 30 31 44 15 05 06 24 25 32 37 08 04 08 11 18 37 45 33 06 14 18 26 36 39 13 15 20 23 26 39 44 28 07 10 19 22 35 40 31 35 36 37 41 44 45 30 07 12 16 34 42 45 04 12 19 20 25 41 45 02 14 21 22 25 30 36 43 05 06 13 14 17 20 07 03 11 24 38 39 44 26 12 14 27 33 39 44 17 01 03 11 24 30 32 07 03 12 14 35 40 45 05 01 03 21 29 35 37 30 01 02 03 15 20 25 43 03 11 14 31 32 37 38 14 25 31 34 40 44 24 02 07 18 20 24 33 37 10 19 22 23 25 37 39 12 13 17 20 33 41 08 11 12 18 21 31 38 08 02 03 04 05 20 24 42 05 07 20 25 28 37 32 02 03 07 15 43 44 04 07 16 17 33 36 40 01 16 20 27 33 35 39 38 01 08 14 18 29 44 20 04 11 20 26 35 37 16 05 11 19 21 34 43 31 02 20 33 35 37 40 10 05 07 28 29 39 43 44 01 03 18 20 26 27 38 04 19 26 27 30 42 07 05 11 13 19 31 36 07 02 06 08 14 21 22 34 04 05 15 16 22 42 02 17 25 35 36 39 44 23 04 05 09 11 23 38 35 05 11 14 29 32 33 12 05 10 19 31 44 45 27 ) len=${#array[*]} i=0 while [ $i -le $len ] do array[$i]=$((array[$i]+0)) i=$(($i+1)) done echo ${array[@]}
개선된 쉘 스크립트
배열부분 생략 #검색할 회차 입력 read range1 read range2 start=$(( ($range1-1) * 7 )) end=$(( $range2*7 - 1 )) #입력한 기간 동안 당첨번호를 출력 while [ $start -le $end ] do echo "${array[$start]} " start=$(( $start + 1 )) done
실행방법 및 결과
jellypo@JellyKing:~$ bash lotto | perl -pe 's/ /\n/g' | sort -n | uniq -c | sort -n 1 (입력) 20 (입력) 1 08 1 18 1 20 1 22 1 35 1 43 1 45 2 01 2 07 2 10 2 11 2 12 2 15 2 17 2 24 2 34 2 36 2 44 3 04 3 13 3 19 3 21 3 23 3 27 3 29 3 32 3 38 4 03 4 06 4 26 4 31 4 33 4 39 4 41 5 09 5 14 6 02 6 16 6 25 6 30 7 37 7 42 8 40 140
앞의 숫자가 빈도, 뒤의 숫자가 당첨 번호입니다.
최종버전
deabak.sh 스크립트 파일
lotto 로또 당첨번호 모음, 한 줄이 각 회에 해당함. 첫째줄이 1회, 끝줄(231라인)이 최근인 231회 번호. 일곱번째 숫자는 행운번호인데 일단 같이 취급함.
deabak.sh
#1/bin/bash echo $1 $2 sed -n "$1,$2p" lotto| tr ' ' '\n' | sort -n | uniq -c | sort -n
사용방법은 커맨드 라인에서
./deabak.sh 12 30
12회부터 30회까지 당첨번호 출현빈도 검색
이런 작업을 굳이 쉘
이런 작업을 굳이 쉘 스크립트로 해야 하는 이유가 있나요?
파이썬이나 루비나 펄 같은 좋은 스크립팅 언어가 많이 있잖아요. :-)
1. 쉘 스크립트로
1. 쉘 스크립트로 시작해버려서
2. 펄은 어느정도 아는데 루비/파이썬은 전혀 몰라서
3. 저도 C로 시작할걸 하는 후회가 ...;
제가 할 줄 아는건 C, bash, perl 정도밖에 없어요.;
할 수
할 수 있으니까.
http://www.faqs.org/docs/bashman/bashref_71.html
느려요.
deabak 배열은 09
deabak 배열은 09 따위가 될 리가 없으므로..
절반 정도로 줄었...
뭔가를 실행시키지 않고 0을 떼버릴 방법이 있을까요 ?
버그수정 [bushi@rose
버그수정
bash 스크립트가 형
bash 스크립트가 형 변환을 스스로 하고, 강제 형변환을 할 수 없게 해놓아서 다른 방법이 없는거 같네요.
제가 문제 해결방법에 따른 수단을 잘못 택한거 같습니다.;; 저기 밑에 sed 혹은 perl로 간단히 하시는 분들 보고 쓰러지는 중.
흠.
엄밀히 말하면 shell script는 아닙니당.
test.list 는 로또 데이터 부분만 추출한 파일입니다
흠2
한번 더 소트하면!
빈도별로 오름차순으로 나옵니다.
흠2
한번 더 소트하면!
빈도별로 오름차순으로 나옵니다.
제가 프로그램 설명을 잘못했네요
중요한걸 깜빡했네요.
일정 기간 동안의 숫자 빈도를 위해 이 프로그램을 만들고 있었습니다. 예를 들면 200회부터 231회까지 1-45각 숫자가 몇 번 나왔는지 알아보려고요. 당첨번호 리스트를 검색할 때마다 손봐야 하는건 불편해서 스크립트로 입력받을 값을 편하게 받을 수 없을까 해서 시작했고요.
좀 정리해서 소스 올릴게요.
이렇게 하시죠.
!!!!!!!!!!!!!!
!!!!!!!!!!!!!!
라인 선택만 하면 되는건가요? info sed 보는 중.
sed -n -e '1,2p' lotto
이렇게 하면 선택된 라인만 출력하는게 가능하네요. (여기서는 1번째 2번째 라인)
'시작위치,$p'은 시작위치부터 $ 파일 끝까지를 p 출력한다는 의미였네요. 이걸 이해 못해서 '$p'로 봤거든요. 따로인걸 몰랐음.
댓글 달기