처음 알게된 case 문 문법?

from Study/C언어 2009/03/06 17:29 view 28125
/* Do not fret, for it is merely a wonderful gcc extension. */
case 'A'...'Z':
case 'a'...'z':
case '0'...'9':

범위를 지정해서 그사이에 있는 경우까지 포함시키는 정규식??
하지만!! gcc에서만 된다는거..-_ㅡ;;
VS6.0 에서 테스트 해보니 모르는 표현이라고 뭐라 하네..
Tag |
  1.   프로그래밍 언어란?

    • 사전적의미 : 컴퓨터의 프로그램을 작성하기 위해 고안된 언어.
    • 우리가 알고 있는 기계어조차도 CPU가 대응시켜준 의미를 따라 움직이는 것이다.
    • 프로그래밍 언어를 통해 의미가 부여된 텍스트 데이터는 소스코드가 되고 다시 프로그램이 된다.
  2. 구조적 프로그래밍 언어

    • 다익스트라가 만든 것으로 프로그램의 논리 구조를 단순화시켜 이해하기 쉬운 작은 서브 프로그램들을 사용해 전체 프로그램을 구성하는 개념.

      • 작은 서브 프로그램들을 이해하면 전체 프로그램을 이해하기가 수월해진다.
  3. 프로그래밍 언어의 분류

    • 어떤 패러다임을 통해 프로그래밍 할 것인지를 결정한 후 그 패러다임에 맞는 프로그래밍 언어를 선택하기 위해서 분류를 한다.
  4. 프로그래밍 언어의 해석

    • 프로그래머가 적어놓은 내용을 해석해 기계에게 직접 명령을 내릴 수 있는 형태로 바꿔주는 컴파일러가 존재한다.
    • 컴파일러는 기계와 프로그래머의 의사소통을 도와주는 통역사와 같은 일을 한다.
    • 오토마타를 사용하여 함수의 파라미터에 함수가 사용될 수 있고, 수 혹은 변수의 대체로 함수의 반환값이 사용될 수도 있는 상황을 '단순화' 한다.
  5. 프로그래밍 언어 VS 일반 언어

    • 프로그래밍 언어는 컴파일러가 그 언어를 이해해야 한다. 컴파일러가 해석할 수 있을 때 코드가 유효해지는 것이다.
    • 사람은 언어를 이해할 때 기계처럼 정해진 대로만 이해하지 않는다. 구문 요소 중 몇 가지를 빼거나 순서를 바꿔도 이해 할 수 있다.
  6. Why is C?

    • 대부분의 언어들이 C 언어를 기반으로 변형 됐으며, 아직까지도 C는 여러 분야에서 많이 사용되고 있다.
    • 표현의 단순함과 기계어와 가까운 형태를 취하고 있다. 인라인 어셈블리를 지원하고 있다.
    • 네이티브 : C언어처럼 기계어로 바로 변환하는 형태로 포인터에 대한 문제를 해결해야 한다.
    • 인터프리터 : 코드의 실행을 인터프리터에서 처리하며 플랫폼을 고려하지 않아도 이기종간의 호환성이 보장된다. 하지만 그만큼 기계에서 멀리 떨어져 있기 때문에 여러가지 근본적인 것들을 이해할 수 없다는 문제를 야기하기도 한다.
  7. C언어는 사라질것인가?

    • C언어는 이미 기계 그 자체가 돼 버렸기 때문에 없어지지 않을 것이다.
    • C는 기계어에 가장 가까운 고급언어로 현재 가장 많이 사용되고 있다.
    • 상당한 플랫폼들에서 C언어를 사용하고 있기 때문에 CPU의 구조가 바뀌면 흔들릴 수도 있지만.....과연?

참고문서 : <마소2009.2월호 special report 2>C언어로 보는 구조적 프로그래밍 언어의 이해-권용휘

이 글은 스프링노트에서 작성되었습니다.

LineTo 구현

from Study/C언어 2007/12/06 16:53 view 26976
- Bresenham algprothm
- 0.5를 더해서 반올림 하는것을 탈피해서 비트 연산을 이용한다.

#include <stdio.h>
#include <windows.h>

#define  MAX_X  36
#define  MAX_Y  20

#define  SetPixel(x,y)    array[y][x]=1

int array[20][36];

void display(void)
{
    int i,j;

    system("cls");
    for( i=0; i<MAX_Y; i++ )
    {
        for( j=0; j < MAX_X; j++ )
        {
            if( array[i][j] )
                printf("□");
            else
                printf("■");
        }
        printf("\n");
    }
}

void line_to( int x1, int y1, int x2, int y2 )
{
    int dx = x2 - x1;
    int dy = y2 - y1;
    double a  = (double)dy/dx;
    double b  = y1 - a*x1;
    int  stepx=1, stepy=1;

    if ( dx < 0 )
        stepx = -1;

    if ( dy < 0 )
        stepy = -1;


    if( abs(dx) > abs(dy) )
    {
        while( x1 != x2 )
        {
            SetPixel( x1, (int)(a*x1+ b + 0.5) );  
            x1 += stepx;
        }
        SetPixel( x1, (int)(a*x1+ b + 0.5) );  
    }
    else
    {
        while( y1 != y2 )
        {
            SetPixel(  (int)( (y1-b)/a + 0.5) , y1 );  
            y1 += stepy;
        }
        SetPixel( (int)( (y1-b)/a  + 0.5) , y1);  
    }

}


void line_to_1( int x1, int y1, int x2, int y2 )
{
    int dx = x2 - x1;
    int dy = y2 - y1;
    double a  = (double)dy/dx;
    double b  = y1 - a*x1;
    int stepx=1, stepy=1;
    double fraction = 0.5 + a;


    if ( dx < 0 )
        stepx = -1;

    if ( dy < 0 )
        stepy = -1;


    if( abs(dx) > abs(dy) )
    {
        while( x1 != x2 )
        {
            SetPixel( x1, y1 );  
            if( fraction >= 1 )
            {
                y1 += 1;
                fraction -= 1;
            }

            fraction += a;
            x1 += 1;
        }
    }
    else
    {
        while( y1 != y2 )
        {
            SetPixel(  (int)( (y1-b)/a + 0.5) , y1 );  
            y1 += stepy;
        }
        SetPixel( (int)( (y1-b)/a  + 0.5) , y1);  
    }

}


void line_to_2( int x1, int y1, int x2, int y2 )
{
    int dx = x2 - x1;
    int dy = y2 - y1;
    double a  = (double)dy/dx;
    double b  = y1 - a*x1;
    int  stepx=1, stepy=1;
    int fraction = dx+2*dy;


    if ( dx < 0 )
        stepx = -1;

    if ( dy < 0 )
        stepy = -1;


    if( abs(dx) > abs(dy) )
    {
        while( x1 != x2 )
        {
            SetPixel( x1, y1 );  
            if( fraction >= 1 )
            {
                y1 += 1;
                fraction -= 2*dx;
            }

            fraction += 2*dy;
            x1 += 1;
        }
    }
    else
    {
        while( y1 != y2 )
        {
            SetPixel(  (int)( (y1-b)/a + 0.5) , y1 );  
            y1 += stepy;
        }
        SetPixel( (int)( (y1-b)/a  + 0.5) , y1);  
    }

}


void line_to_3( int x1, int y1, int x2, int y2 )
{
    int dx = x2 - x1;
    int dy = y2 - y1;
    double a  = (double)dy/dx;
    double b  = y1 - a*x1;
    int  stepx=1, stepy=1;
    int fraction = (dy<<1) - dx;


    if ( dx < 0 )
        stepx = -1;

    if ( dy < 0 )
        stepy = -1;

    dx <<= 1;
    dy <<= 1;

    if( abs(dx) > abs(dy) )
    {
        while( x1 != x2 )
        {
            SetPixel( x1, y1 );  
            if( fraction >= 0 )
            {
                y1 += 1;
                fraction -= dx;
            }

            fraction += dy;
            x1 += 1;
        }
    }
    else
    {
        while( y1 != y2 )
        {
            SetPixel(  (int)( (y1-b)/a + 0.5) , y1 );  
            y1 += stepy;
        }
        SetPixel( (int)( (y1-b)/a  + 0.5) , y1);  
    }

}


void line_to_4( int x1, int y1, int x2, int y2 )
{
    int dx = x2 - x1;
    int dy = y2 - y1;
    int  stepx=1, stepy=1;
    int fraction;


    if ( dx < 0 )
    {
        dx = -dx;
        stepx = -1;
    }

    if ( dy < 0 )
    {
        dy = -dy;
        stepy = -1;
    }

    dx <<= 1;
    dy <<= 1;

    if( dx >= dy )
    {
        fraction = dy - (dx>>1);
        while( x1 != x2 )
        {
            SetPixel( x1, y1 );  
            if( fraction >= 0 )
            {
                y1 += stepy;
                fraction -= dx;
            }

            fraction += dy;
            x1 += stepx;
        }
    }
    else
    {
        fraction = dx - (dy>>1);
        while( y1 != y2 )
        {
            SetPixel( x1, y1 );  
            if( fraction >= 0 )
            {
                x1 += stepx;
                fraction -= dy;
            }

            fraction += dx;
            y1 += stepy;
        }
    }
    SetPixel( x1, y1 );  
}


int main()
{
    line_to_4(8, 15 , 0, 0 );
    display();
}

문자열 함수의 구현

from Study/C언어 2007/11/29 16:22 view 27430
1. my_strcpy( strcpy )
#include <stdio.h>
#include <assert.h>

void my_strcpy( char * dest, char * src )
{
    assert(src!=0 && dest!=0);
    while( (*dest++ = *src++) != 0 )
        // nothing ;
}

2. my_strlen( strlen )
// 자료형끼리의 길이를 빼주는 방식으로 구한다.
// 포인터를 이용하는 방식을 선호해보자.
int my_strlen( char* arg )
{
    char *base = arg;

    for( ; *arg != '\0'; ++arg)
        NULL/*nothing*/;
   
    return (int)(arg - base);    // 포인터와 포인터를 빼면 그 길이가 나온다.
}

3. my_strcat( strcat )
// dest의 오버플로우는 보장해주지 않는다. 사용자가 해야 하는 일.
void my_strcat( char* dest, char* src )
{
    while( *dest != '\0' )
        ++dest;    // NULL 위치를 가리키는 포인터로 만든다.

    while( (*dest++ = *src++) != '\0' )
        /*nothing*/;
}

4. reverse( reverse )
// 손바닥을 뒤집듯이 처음과 끝부터 차례대로 바꾼다.
// 가운데, 즉 역전 되기 전까지 바꿔나간다. => | <=
// 한글이 섞여 있다면 안된다. 2바이트랑 1바이트랑 바꾸기가 힘들다.
void reverse( char* arg )
{
    int len = strlen( arg );
    int i, j, t;

    for( i = 0, j = len - 1; i < j; ++i, --j )
    {
        t = arg[i];
        arg[i] = arg[j];
        arg[j] = t;
    }
}

5. swap( swap )
void swap( void* dest, void* src, int size )
{
    void *temp = malloc( size );

    memcpy( temp, dest, size );
    memcpy( dest, src, size );
    memcpy( src, temp, size );

    free( temp );
}

6. my_strcmp( strcmp )
int my_strcmp( char* dest, char* src )
{
    int ret;

    // 같았는데 '\0' 이 아니라면 또 비교하고 .. 비교하고.
    // 같지 않다면 음수나 양수를 리턴시켜준다.
    // while( ( ret = *dest++ - *src ) == 0 && *src++ != '\0' )
    while( 1 )
    {
        if( ( ret = *dest++ - *src ) != 0 || *src++ == '\0' )
            break;
    }

    return ret;
}

7. my_strchr( strchr )
char* my_strchr( char *dest, int src )
{
    for( ; *dest != src; ++dest )
        if( *dest == 0  )
            return 0;

    return dest;
}

8. my_strstr( strstr )
char* my_strstr( char* dest, char* src ) {
    int i, j;
    int len_dest = strlen(dest);
    int len_src  = strlen(src);

    for( i = 0; i < len_dest - len_src+1; ++i )
    {
        for( j = 0; j < len_src; ++j )
        {
            if( dest[i+j] != src[j] )
                break;
        }
        if( j == len_src )    // 끝까지 루프를 돌아으므로 같다는 의미..
        {
            return dest+i;
        }
    }

    return 0;
}

9. my_strspn( strspn ) - 지정한 토큰이 아닌 곳의 인덱스를 반환한다.
int my_strspn( char* dest, char* src )
{
    int i, j;
    int len_dest = strlen( dest );
    int len_src  = strlen( src );

    for( i = 0; i < len_dest; ++i )
    {
        for( j = 0; j < len_src; ++j )
        {
            if( dest[i] == src[j] )
                break;
        }

        if( j == len_src )
            return i;
    }

    return i;    // 끝까지 갔다면 NULL의 인덱스가 리턴된다.
}

10. my_strtok( strtok )
char * my_strtok(char * str, char * del)
{
    static char *curr;
    char *sbegin, *send;
   
    sbegin  = str ? str : curr;
    if (!sbegin)
        return 0;
   
    sbegin += strspn(sbegin,del);
    if (*sbegin == 0)
    {
        curr = 0;
        return 0;
    }
    send = strpbrk( sbegin, del);
    if (send && *send )
        *send++ = 0;
    curr = send;

    return sbegin;
}

비트 플래그

from Study/C언어 2007/11/28 21:10 view 31084

1. 기본( &(검사), |(추가),  &= ~(삭제) )

more..


2. 배열을 사용한 비트 플래그

more..


3. 매크로를 이용한 비트 플래그 연산( http://lxr.linux.no/source/include/linux/posix_types.h )

more..


4.2(화) 가변 인수에 맛보기..

from Study/C언어 2007/04/02 20:18 view 25076

int __cdecl printf (

        const char *format,

        ...

        )

/*

 * stdout 'PRINT', 'F'ormatted

 */

가변인수란 인수의 개수와 타입이 미리 정해져 있지 않은 것으로 이런 인수를 사용하는 함수를 가변 인수 함수라 한다.

번째 인수(고정인수) : format으로 문자열 상수를 의미하며 서식 문자열이라고도

번째 인수(가변인수) : 이후부터는 타입과 인수 이름이 명시되어 있지 않으며 대신 생략 기호인(ellipsis) 적혀 있다. – 생략기호는 컴파일러에게 이후의 인수에 대해서는 개수와 타입을 점검하지 않도록 하는데 기호에 의해 가변 인수가 가능해진다.

printf("%d", 1,2,3);   // %d 하나가 가변인수 하나 인식


int GetSum(int num, ...)

{

        int sum=0;

        int i;

        va_list ap;

        int arg;

 

        va_start(ap,num);

        for (i=0;i<num;i++) {

               arg=va_arg(ap,int);

               sum+=arg;

        }

        va_end(ap);

        return sum;

}


va_list ap : 함수로 전달되는 인수들은 스택에 저장되며 함수는 스택에서 인수를 꺼내 쓴다.

va_start(ap, Fix) :
가변 인수를 읽기 위한 준비를 하는 것으로 ap포인터 변수가 번째 가변인수를 가리키도록 초기화 한다
.

va_arg(ar,
인수타입) : 가변인수를 실제로 읽는 명령임. va_start ap 번째 가변 인수번지로 맞추어 주므로 ap위치에 있는 값을 읽으면 된다. ap번지에 있는 값의 타입을 지정해 줘야 (정수를 읽으면-va_arg(ap, int), 실수일경우
-va_arg(ap, double) )

va_end(ap) :
가변인수를 읽은 뒷정리를 하는 것.(없어도 )


4.2(월) min, max의 활용

from Study/C언어 2007/04/02 16:30 view 27771
#define max(a, b)  (((a) > (b)) ? (a) : (b))
frame = max(frame-10, 10);

frame은 10미만값을 가질 수 없다.

#define min(a, b)  (((a) < (b)) ? (a) : (b))
frame = min(frame+10, 1000)

frame은 1000을 초과 할 수 없다.

if문으로 할수도 있겠지만 이렇게 범위를 지정 해 놓으니 훨씬 좋아 보인다..
Tag |

3.28(수) strstr, strtok 함수

from Study/C언어 2007/03/28 18:38 view 38626

함수 개요

#include <string.h>

char *strtok( char *str, const char *set);

char *strstr( const char *src, const char *sub);


참고 : 2007/11/29 - [Study/C언어] - 문자열 함수의 구현

strstr 함수는 표준 C에서 처음 도입한 함수다. 이는 문자열 str 안에서 문자열 sub가 처음으로 나오는 위치를 찾아 해당 위치를 가리키는 포인터를 반환한다. 문자열 sub가 문자열 src에 한 번도 나오지 않는 경우에는 널 포인터를 반환한다.

strtok 함수는 문자열 str을 문자열 set에 나온 문자로 구분되는 토큰으로 나눌 때 사용한다. 각각의 토큰을 분리하기 위해 strtok 함수를 여러 번 호출하며, 도중에 문자열 set의 내용을 바꿀 수 있다. strtok 함수를 처음 호출할 때는 str에 문자열을 제공하며, 그 뒤에 이어지는 호출에서는 첫 번째 인자로 널 포인터를 주게 된다. 그러면 strtok함수는 이전에 찾은 토큰의 뒷부분부터 이어 검색을 진행한다.(strtok 함수를 사용해서 문자열 안의 토큰을 검색하는 과정에서 처음 제공된 문자열 str을 도중에 수정하면 안 된다.)

과정을 더 자세히 설명하면, 매개 변수 str에 널 포인터가 제공되지 않으면, strtok 함수는 문자열 str에서 set 에 존재하는 모든 문자를 건너뛰게 된다. 만약 문자열 str이 문자열 set의 문자로만 구성되어 있는 경우, strtok 함수는 토큰을 찾을 수 없기에 결과로 널 포인터를 반환한다. 이때 내부적으로 상태를 저장하기 위해 사용하는 포인터는 널 포인터로 설정된다. 문자열 str에 문자열 set에 나오지 않는 문자가 있는 경우, 내부 상태 포인터가 str에서 해당 문자를 가리키게 되고, str로 널 포인터가 제공된 것처럼 함수 실행이 계속된다.

str과 내부 상태 포인터 모두가 널 포인터인 경우, strtok 함수는 널 포인터를 반환하고 내부 상태 포인터는 널 포인터로 남는다.(이는 모든 토큰을 찾은 이후에 추가로 strtok 함수가 호출되는 경우를 위해서다.) str 이 널 포인터고 내부 상태 포인터가 널 포인터가 아닌 경우, 함수는 내부 상태 포인터가 가리키는 위치부터 시작해서 처음 제공된 str의 나머지 부분에서 set에 포함된 문자를 찾게 되고, 그와 같은 문자를 찾으면 해당 문자를 널 문자로 덮어쓴다. 함수의 결과로는 내부 상태 포인터의 값을 반환하고, 반환 이후에 내부 상태 포인터의 값은 저장된 널 문자 바로 뒤의 문자를 가리키도록 수정된다. 그러한 문자를 찾지 못하는 경우, strtok 함수는 내부 상태 포인터의 값을 반환하고 내부 상태 포인터를 널 포인터로 설정한다.

/*
다음프로그램은표준입력스트림으로부터문자열을입력받아strtok 함수를통해입력받은
라인을단어단위로나누어표준스트림으로출력한다. 이때단어는공백, 쉼표, 마침표, 인용부호,
물음표로구분된다고가정한다.
*/


예제 1.

#include <stdio.h>
#include <string.h>

int main() { char  hp[] = "080)(010)1234-4567";
    char  *p;
                  
    p = strtok( hp, "-()" );

    while( p )
    {
        printf("%s\t", p);
        p = strtok( 0, "-()");
    }

    printf("\n");

    return 0;
}

예제 2.


#include <stdio.h>
#include <string.h>

#define LINELENGTH 80
#define SEPCHARS " .,?\"\n"

int main(void)
{
   
char line[LINELENGTH];
   
char *word;

   
while(1)
    {
        printf(
"\nNext line? (empty line to quit)\n");
        fgets(line, LINELENGTH, stdin);
       
if(strlen(line) <= 1)
           
break;              //프로그램종료
        printf("That line contains these words: \n");
        word = strtok(line, SEPCHARS);              
//첫번째단어를찾음
        while(word != NULL)
        {
            printf(
"\"%s\"\n", word);
            word = strtok(
NULL, SEPCHARS);   //다음단어를찾음
        }
    }
}

Tag |

'배열 포인터' 왠지 포인터 배열을 떠오르지만 2007/03/22 - [Study] - 이차원배열과 포인터 익히기(참고) type(*변수)[]type*변수[x] 를 확연히 구분 짓는 ( ) 괄호를 생각해보면 쉽게 구분 짓을 수 있다.

1. type*변수[]

이 선언문에 사용된 *와 []는 둘 다 구두점이다. *가 앞쪽에 있으므로 변수는 먼저 정수형 포인터가 되고 다음으로 []에 의해 그런 포인터 변수 5개를 모아 배열을 선언하게 된다. 즉, 포인터배열은 포인터 타입의 모임을 정의한 것이라 할 수 있다. 이것의 쓰임새를 살펴보면  

사용자 삽입 이미지



*메모리를 아껴쓰기 위해 태어난 포인터라 생각해도 좋을 것이다. 2차원 배열을 쓴다면 행*열*타입 으로 메모리를
차지하는 byte를 계산 하겠지만 포인터배열에서는 행은 똑같지만 열에서 큰 차이를 보인다. 가령 1반의 학생수가 100명이고 2반의 1명이라면 어떠할까??

2차원 배열에서는 ar[2][100]; 이라고 선언해야 할 것이고 포인터배열에서는 *ar[2] ; 이란 선언을 통해 동적인 메모리 할당을 할 수 있는 것이다. 이러한 개념만 확실히 느끼고 있다면 앞으로 더 느끼는게 많을 듯 싶다.

여기서 또 하나 집고 가야 부분은 포인터배열을 통해 문자열을 입력 받았을 때이다.

사용자 삽입 이미지


arps[0]은 주소를 저장할 수 있는 포인터 변수라 생각하면 된다. *arps[]은 포인터 타입의 배열이라고 생각하기 바란다. 이 포인터 변수는 단지 상수영역(constant)에 있는 문자열 "고양이"등의 시작주소를 가리키는 거라 생각해야 한다. 이러한 문자열은 하나의 상수이기 때문에 변경을 하지 못한다. 이차원배열을 통해 입력 받는 문자열은 스택영역(stack)에 저장되어 얼마든지 접근하여 변경가능 하는 거랑 다른 점이라 할 수 있다.
참고 : 포인터배열

2. type(*변수)[2차 첨자 크기]

변수를 포인터형으로 변환한다. 그리고 나서 [2차첨자크기]만큼의 크기를 갖는 이차원 배열의 번지를 담는 것이다. 2차 첨자 크기는 반드시 기재해야 가리킬 배열의 전체 크기를 구할 수 있다.

*2차원배열을 포인터로 받고 싶을 때 사용한다고 보면 된다.물론 그 이상의 배열도 가능하다.

사용자 삽입 이미지

함수의 인수가 pi[][3]은 (*pi)[3]과 동일하다. 다만 인수가 포인터인지 배열을 받을 포인터인지 무엇을 강조하느냐의 차이 있을 뿐이다.

**포인터 배열은 결국은 배열이고 배열 포인터는 결국은 포인터이다.**
Tag |

C를 공부하다 중간고지인 포인터를 익히기 되면 void형 포인터라는 복병을 만나게 된다.

void *vp;    //대상체의 타입을 명시하지 않는 특별한 포인터형 이다.


  1. 임의의 대상체를 가리킬 수 있다.
    1. 대상체가 정해져 있지 않다는 말은 어떠한 대상체도 가리키지 못한다는 뜻이 아니라 임의의 대상체를 가리킬 수 있다는 얘기와도 같다. 선언할 때 대상체의 타입을 명시하는 일반적인 포인터는 지정한 타입의 대상체만 가리킬 수 있지만 void형 포인터는 어떠한 대상체라도 가리킬 수 잇다.
      void형 포인터는 임의의 포인터를 대입 받을 수 있지만 반대로 임의의 포인터에 void형 포인터를 대입 할 때는 반드시 캐스팅을 해야 한다.
      pi = (int* )vp;    //int*pi
      pd=(double*)vp;    //double* pd

  2. *연산자를 쓸 수 없다.
    1. void형 포인터는 임의의 대상체에 대해 번지값 만을 저장하며 이 위치에 어떤 값이 들어 있는지는 알지 못한다. 따라서 *연산자로 이 포인터가 가리키는 메모리의 값을 읽을 수 없다. 대상체의 타입이 정해져 있지 않으므로 포인터가 가리키는 위치에서 몇 바이트를 읽어야 할지, 또 읽어낸 비트를 어떤 식으로 해석해야 할지를 모르기 때문이다. 만약 vp번지에 저장된 값이 정수형이라는 것을 확실히 알고 읽고 싶다면,

      *(int *)vp;        
      //vp를 잠시 정수형 포인터로 바꾼 후 번지의 정수값을 읽는다.

  3. 증감연산자를 쓸 수 없다.
    1. 대상체의 타입이 정해져 있지 않으므로 증감 연산자도 곧바로 사용할 수 없다.

      vp=(int *)vp + 1;    
      //vp를 잠시 int*로 캐스팅한 후 1을 더하면 4바이트를 더한다.

void형 포인터의 특징에 대해 간단하게 요약해 보면 대상체가 정해져 있지 않으므로 임의의 번지를 저장할 수 있지만 *연산자로 값을 읽거나 증감연산자로 이동할 때는 반드시 캐스트 연산자가 필요하다. 순수하게 메모리의 한 지점을 가리키는 기능만 가지는 포인터 이기 때문이다.

참고 : 이중포인터(winapi)

Tag |