[C] 소수 구하는 코드 짜보고 있는데 배열 크기 관련해서 도움 요청합니다.

majesticer13의 이미지

C에서 배열 크기 제한이 존재하나요?

int에서 기본적으로 제공 하는 크기를 넘는 자리 수의 소수를 구하는 코드를 짜봤는데

배열의 수가 일정 이상 할당되면 제대로 작동이 되지 않는 것 같습니다.

혹시 제 노트북 성능 문제인가 해서 구글 클라우드 컴퓨터로 슈퍼 컴에 돌려봐도 똑같네요 ㅠㅠ

취미 삼아 가끔 코드 써보는 초보다 보니 이렇게 막히면 한계가 찾아 오네요ㅠㅠ

혹시 어떤 부분을 어떻게 고쳐야 할지 도움 받을 수 있을까요?

#include <stdio.h>
#include <time.h>
#include <stdlib.h>
 
#define PRINUM 698354
 
#define MOVE 1000000000
 
 
 
int main()
{
	clock_t start_t,end_t;
	float timer;
	start_t=clock();
 
//////////////////////////////////////////////////////////////
	char cmd_buffer[162];
	int prime[PRINUM];
	int division[PRINUM];
	int calc[PRINUM];
	int i1,i2;
	int j1,j2,j3;
 
	//배열 초기화
	for(i1=PRINUM;i1>=0;i1--)
	{
		prime[i1]=0;   
		division[i1]=0;
		calc[i1]=0;
	}	
	prime[0]=2;
	division[0]=2;
 
 
	for(;;)
	{	
	  	for(i1=0;i1<=PRINUM;i1++)
                {
			calc[i1]=prime[i1];
		}
 
		for(;;)
		{
			//전체 크기 비교
			j1=0;
			for(i1=PRINUM;i1>=0;i1--)
			{
				if(prime[i1]>=division[i1])
				{
					j1=1;break;
				}
				else if(prime[i1]<division[i1])
	                	{
        	                	j1=2;break;
                		}
			}	
 
 
 
			//뺄샘 반복
			if(j1==1)
			{
				for(i1=0;i1<PRINUM;i1++)
				{
					calc[i1]-=division[i1];
 
					j3=0;
					for(i2=PRINUM;i2>=0;i2--)
					{
						if(calc[i2]<division[i2])
						{
		 					j3=1;break;
						}
					}
 
 
 
					for(i2=PRINUM;i2>0;i2--)
					{
						if(calc[i2]>0)
						{
							if(calc[i2-1]<MOVE)
							{
								calc[i2]--;
								calc[i2-1]+=MOVE;
							}
						}
					}
 
 
 
				}
			}
			else if(j1==2)
			{
				break;
			}
			if(j3==1)
			{
				break;
			}
		}
 
		j2=0;
 
		//배열 동일성 확인
		for(i1=0;i1<=PRINUM;i1++)
		{
			if(prime[i1]!=division[i1])
      			{
				j2++;
			}
		}
		j3=0;
		for(i1=0;i1<=PRINUM;i1++)
                {
			j3+=calc[i1];
                }
 
 
		if(j3==0)
		{
			if(j2==0)
			{
				for(i1=PRINUM;i1>=0;i1--)
        	       	 	{
                	        	printf("%d ",prime[i1]);
					sprintf(cmd_buffer,"echo -n %d >> /home/libert/prime/prime", prime[i1]);
					system(cmd_buffer);
              	  		}
				printf("\n");
                                system("echo "" >> /home/libert/prime/prime");
 
			}
			for(i1=0;i1<=PRINUM;i1++)
                	{
                        	division[i1]=0;
                        	calc[i1]=0;
                	}
                	division[0]=1;
 
			prime[0]++;
			for(i1=0;i1<PRINUM;i1++)
	                {
        	                if(prime[i1]>MOVE)
                	        {
                        	        prime[i1]-=MOVE;
                                	prime[i1+1]++;
                        	}
                	}
 
		}
		division[0]++;
		for(i1=0;i1<PRINUM;i1++)
		{
			if(division[i1]>MOVE)
			{
				division[i1]-=MOVE;
				division[i1+1]++;
			}
		}
	}
 
 
 
 
 
 
//////////////////////////////////////////////////////////////
 
	end_t=clock();
	timer=(float)(clock()-start_t)/CLOCKS_PER_SEC;
	printf("소요시간 : %.6fs \n",timer);
	sprintf(cmd_buffer,"echo -ne \n\n소요시간 : %.6fs \n >> /home/libert/prime/prime",timer);
	system(cmd_buffer);
}

세벌의 이미지

컴파일 할 때 에러 뿐 아니라 경고도 함께 나오도록 해서 경고 메시지를 보시면 도움이 될 겁니다.

majesticer13의 이미지

답변 감사합니다. 검색해보니 gcc 옵션에 -W -Wal 정도면 될까하는데 추천해 주실만한 다른 방법이 있을까요?

majesticer13의 이미지

실행 시간 때문에 선언 했던 end_t 하나만 걸리고 실제 코드에서는 뭔가 걸리는 게 없네요 ㅠㅠ

라스코니의 이미지

처음 배울때 하는 흔한 실수 중의 하나죠.
메모리는 실제로는 4G~32G도 할당할 수 있죠. 쉽지는 않지만 여러 테크닉을 쓰면 충분히 가능합니다. 이때 malloc()을 써야 합니다.

내부 변수로서의 배열은 stack에 잡히는데 시스템마다 기본 스택 사이즈가 다릅니다.
PRINUM은 698,354, 즉 681kbyte 인데 이것을 int (4 byte)형으로 3개를 선언하면
총 필요한 스택 사이즈는 681k * 4 * 3 = 8,172 kbyte 즉 7 Mbyte가 됩니다.
개발 환경이 리눅스이면 'ulimit -a' 명령으로 확인해 보세요. 현재 stack max size가 얼마인지.

10 kbyte 이상이 필요하면 malloc()을 써서 할당받아서 사용하세요. 이 메모리는 heap 영역으로부터 가져와서 할당됩니다. stack이 아니라.

댓글 달기

Filtered HTML

  • 텍스트에 BBCode 태그를 사용할 수 있습니다. URL은 자동으로 링크 됩니다.
  • 사용할 수 있는 HTML 태그: <p><div><span><br><a><em><strong><del><ins><b><i><u><s><pre><code><cite><blockquote><ul><ol><li><dl><dt><dd><table><tr><td><th><thead><tbody><h1><h2><h3><h4><h5><h6><img><embed><object><param><hr>
  • 다음 태그를 이용하여 소스 코드 구문 강조를 할 수 있습니다: <code>, <blockcode>, <apache>, <applescript>, <autoconf>, <awk>, <bash>, <c>, <cpp>, <css>, <diff>, <drupal5>, <drupal6>, <gdb>, <html>, <html5>, <java>, <javascript>, <ldif>, <lua>, <make>, <mysql>, <perl>, <perl6>, <php>, <pgsql>, <proftpd>, <python>, <reg>, <spec>, <ruby>. 지원하는 태그 형식: <foo>, [foo].
  • web 주소와/이메일 주소를 클릭할 수 있는 링크로 자동으로 바꿉니다.

BBCode

  • 텍스트에 BBCode 태그를 사용할 수 있습니다. URL은 자동으로 링크 됩니다.
  • 다음 태그를 이용하여 소스 코드 구문 강조를 할 수 있습니다: <code>, <blockcode>, <apache>, <applescript>, <autoconf>, <awk>, <bash>, <c>, <cpp>, <css>, <diff>, <drupal5>, <drupal6>, <gdb>, <html>, <html5>, <java>, <javascript>, <ldif>, <lua>, <make>, <mysql>, <perl>, <perl6>, <php>, <pgsql>, <proftpd>, <python>, <reg>, <spec>, <ruby>. 지원하는 태그 형식: <foo>, [foo].
  • 사용할 수 있는 HTML 태그: <p><div><span><br><a><em><strong><del><ins><b><i><u><s><pre><code><cite><blockquote><ul><ol><li><dl><dt><dd><table><tr><td><th><thead><tbody><h1><h2><h3><h4><h5><h6><img><embed><object><param>
  • web 주소와/이메일 주소를 클릭할 수 있는 링크로 자동으로 바꿉니다.

Textile

  • 다음 태그를 이용하여 소스 코드 구문 강조를 할 수 있습니다: <code>, <blockcode>, <apache>, <applescript>, <autoconf>, <awk>, <bash>, <c>, <cpp>, <css>, <diff>, <drupal5>, <drupal6>, <gdb>, <html>, <html5>, <java>, <javascript>, <ldif>, <lua>, <make>, <mysql>, <perl>, <perl6>, <php>, <pgsql>, <proftpd>, <python>, <reg>, <spec>, <ruby>. 지원하는 태그 형식: <foo>, [foo].
  • You can use Textile markup to format text.
  • 사용할 수 있는 HTML 태그: <p><div><span><br><a><em><strong><del><ins><b><i><u><s><pre><code><cite><blockquote><ul><ol><li><dl><dt><dd><table><tr><td><th><thead><tbody><h1><h2><h3><h4><h5><h6><img><embed><object><param><hr>

Markdown

  • 다음 태그를 이용하여 소스 코드 구문 강조를 할 수 있습니다: <code>, <blockcode>, <apache>, <applescript>, <autoconf>, <awk>, <bash>, <c>, <cpp>, <css>, <diff>, <drupal5>, <drupal6>, <gdb>, <html>, <html5>, <java>, <javascript>, <ldif>, <lua>, <make>, <mysql>, <perl>, <perl6>, <php>, <pgsql>, <proftpd>, <python>, <reg>, <spec>, <ruby>. 지원하는 태그 형식: <foo>, [foo].
  • Quick Tips:
    • Two or more spaces at a line's end = Line break
    • Double returns = Paragraph
    • *Single asterisks* or _single underscores_ = Emphasis
    • **Double** or __double__ = Strong
    • This is [a link](http://the.link.example.com "The optional title text")
    For complete details on the Markdown syntax, see the Markdown documentation and Markdown Extra documentation for tables, footnotes, and more.
  • web 주소와/이메일 주소를 클릭할 수 있는 링크로 자동으로 바꿉니다.
  • 사용할 수 있는 HTML 태그: <p><div><span><br><a><em><strong><del><ins><b><i><u><s><pre><code><cite><blockquote><ul><ol><li><dl><dt><dd><table><tr><td><th><thead><tbody><h1><h2><h3><h4><h5><h6><img><embed><object><param><hr>

Plain text

  • HTML 태그를 사용할 수 없습니다.
  • web 주소와/이메일 주소를 클릭할 수 있는 링크로 자동으로 바꿉니다.
  • 줄과 단락은 자동으로 분리됩니다.
댓글 첨부 파일
이 댓글에 이미지나 파일을 업로드 합니다.
파일 크기는 8 MB보다 작아야 합니다.
허용할 파일 형식: txt pdf doc xls gif jpg jpeg mp3 png rar zip.
CAPTCHA
이것은 자동으로 스팸을 올리는 것을 막기 위해서 제공됩니다.