이러한 관계가 성립되지요
그럼 이를 염두해 보고 문제를 풀어보겠습니다.
처음이니 차례차례 갈께요.
개념적으로 이루어지는 순서는 이렇습니다.
1. 우선 정사각형 내에서 난수제조기를 이용해서 한 점을 뽑는다
2. 이 점이 원안에 들어가는지 확인한다
3. 무수히 많이 반복해서 (들어간 점들/총 점의 갯수)를 이융해 p를 구한다
4. 4*p로 파이를 계산한다
참 쉽지요?
그럼 한줄한줄 가보겠습니다.
1. 우선 정사각형을 정의해야합니다.
xy좌표계에 가장 쉽게 할 수 있는 것은
x, y각각 -1에서 1까지 이지요.
그러면 난수제조기로 -1에서 1 사이에 균일분포된 점들을 뽑아야합니다
두개를 뽑아 하나는 x 하나를 y라고 부르면 됩니다.
그럼 첫번째 문제:
이렇게 균일분포된 (x,y)행 벡터를 만들어보세요
(rand를
이용해야 합니다. rand는 0에서 1까지 균일분포되어있기 때문에
-1에서 1로 바꾸려면 약간의 창의성이 필요합니다. help rand를 쳐보면 도움될 수도 있습니다.)
(답은 아래에 흰글씨로 써놓았습니다.)
>> xy=2*rand(1,2)-1
xy =
-0.7460 0.8268
2. 1에서 뽑은 이 (x,y)가
원 안에 들어가는지 판단하는 function을 쓰시오
input에 2개의 숫자가 들어가고 output에는 원 안에 들어갈 시
1, 들어가지 않을 시 0이 나오도록 합니다.
(function [check]=함수이름(x,y) 로 시작합니다)
function [check]=circle_check(x,y)
if (x.^2+y.^2)<=1
check=1;
else
check=0;
end
end
3. 새로운 script파일을 작성해 이 무작위로 정사각형 내에서 점을 100번 뽑은 후
(2) 에서 작성한 함수를 이용, 원 안에 몇번 들어가는지 세어 보시오
count=0;
for i=1:100
xy=2*rand(1,2)-1;
circle_result = circle_check(xy(1),xy(2));
count=count+circle_result;
end
count
자 이부분이 다소 난해합니다.
우선 count=0으로 정의했는데요
여기에선 몇번나오는지 셀 수 있도록
counter의 개념으로 정의했습니다.
앞으로 원 안에 들어가면 1씩 더할 것입니다.
그리고 for 문을 이용해 i=1:100, 즉 100번 돌립니다.
xy=2*rand(1,2)-1은 (1)에서 썼던 것이지요
circle_result = circle_check(xy(1), xy(2))에서는
(2)에서 작성한 함수를 이용하고
xy라는 행벡터의 첫번쨰 요소를x, 두번째 요소를 y에 넣습니다.
그리고 함수의 결과값을 circle_result에 일단 저장합니다.
원에 들어갔으면 circle_result가 1, 들어가지 않았으면 0이겠지요?
이것을 count=count+cirle_result을 이용해
원에 들어갈때마다 count에 1씩 더해줍니다.
0일경우에도 더하기는 하지만 0을 더하니 똑같겠지요?
그리고 마지막에 count를 입력해주어 결과값을 출력합니다
count =
76
저의경우엔 76번 들어갔네요
4. (3)에서 쓴 script를 고쳐 몇번 들어갔는가가 아니라
100번중 몇번인지 확률을 구하고 확률에 4를 구해 파이 값을 추산해보시오
(마지막줄만 고치시면 됩니다)
count=0;
for i=1:100
xy=2*rand(1,2)-1;
circle_result
= circle_check(xy(1),xy(2));
count=count+circle_result;
end
my_pi=count/100*4
마지막줄에 my_pi라는 새로운 변수로 정의했습니다.
pi는 이미 정의되어있으니 피하기로 했구요
간단하게 횟수/100*4를 이용했습니다.
한번 돌려볼께요
my_pi =
3.2400
5. (4)에서 쓴 script를 고쳐 100번이 아닌 n번 반복하게 하며
n은 첫번째줄에 정의하도록 하시오
n=1000;
count=0;
for i=1:n
xy=2*rand(1,2)-1;
circle_result = circle_check(xy(1),xy(2));
count=count+circle_result;
end
my_pi=count/n*4
보시면 첫째줄에 n=1000이라고 정의할 수 있는 행을 넣었고
for 문에 1:n까지
그리고 my_pi=count/n*4로 바꾸어주었습니다.
이렇게하면 처음에 n을 원하는 숫자로 바꾸어 매트랩이 몇번 반복할지 정할 수 있습니다.
한번 실행해보겠습니다.
my_pi =
3.1240
횟수가 많아지니 원주율에 조금 가까워졌네요
6. n을 백만으로 돌려서 파이의 근사값을 구하시오
n=1000000;
count=0;
for i=1:n
xy=2*rand(1,2)-1;
circle_result
= circle_check(xy(1),xy(2));
count=count+circle_result;
end
my_pi=count/n*4
자 편리하게 n만 1,000,000으로 바꾸었습니다.
돌려보면 조금 시간이 걸립니다.
my_pi =
3.1418
원주율의 실제갑은 3.14159265정도 되니
제법 가깝습니다.
--
굉장히 간단한 첫번째 문제를 풀어봤는데요
어때요 어렵지 않죠?
실제로 이러한 방식으로 파이를 구하는 것은 매우 비효율적이며
일반적으로 컴퓨터가 계산하는 것은 더 빠르게 수렴하는 수열이 있지만
for문과 rand를 써보기 위해 예제를 만들었습니다
(사실 난수만으로 이루어진 10000*2의 벡터를 이용하는게 훨씬 계산이 빠르지만
연습을 위행 일단 이렇게 진행했습니다)
앞으로 조금씩 난이도를 올려가면서 예제를 준비해보려 하겠습니다
읽어주시는분께 감사드립니다.