[C++ 정리] 함수로 인자를 전달하는 유형 2015-06-15

자료의 형태별로 함수에 인자를 전달하는 방법을 정리해본다.

#include "stdafx.h"
#include <iostream>

using namespace std;

int TestFuncBasic(int arg1, int arg2);
void TestFuncPointer(int arg1, int* arg2);
void TestFuncReference(int arg1, int& arg2);
void TestFuncArray(char arg[]);
void TestFuncMultiArray(int arg1[][2], int arg2[][2][2]);

int _tmain(int argc, _TCHAR* argv[])
{
	// Ex1> basic : 변수를 전달하고 리턴을 받는다.
	int valueBasic1 = 100;
	int valueBasic2 = 100;
	int valueBasicReturn;
	valueBasicReturn = TestFuncBasic(valueBasic1, valueBasic2);

	cout << "Ex1> " << valueBasicReturn << "\n";

	// Ex2> pointer : 변수와 포인터를 전달하고 포인터를 활용해 계산된 값을 읽는다.
	int valuePointer1 = 100;
	int valuePointerReturn = 0;
	int* valuePointer2 = &valuePointerReturn;
	TestFuncPointer(valuePointer1, valuePointer2);

	cout << "Ex2> " << valuePointerReturn << "\n";

	// Ex3> reference : 변수를 전달하고 참조를 이용해 계산된 값을 읽는다.
	int valueReference1 = 100;
	int valueReference2 = 100;
	TestFuncReference(valueReference1, valueReference2);

	cout << "Ex3> " << valueReference2 << "\n";

	// Ex4> array : 배열 전달하고 참조를 이용해 수정된 값을 읽는다.
	// ※ 실제로는 포인터를 전달함에 유의할것
	char valueArray[100] = "Array Tast";

	TestFuncArray(valueArray);

	cout << "Ex4> " << valueArray << "\n";

	// Ex5> array : 다차원 배열 전달시에는 맨앞쪽 대괄호를 비워둔다.
	int multiArray1[2][2] = {
		{ 1, 2 },
		{ 3, 4 }
	};
	int multiArray2[2][2][2] = {
		{
			{ 1, 2 },
			{ 3, 4 }
		},
		{
			{ 5, 6 },
			{ 7, 8 }
		}
	};

	TestFuncMultiArray(multiArray1, multiArray2);

	cout << "Ex5> " << multiArray1[0][0] << "  //  " << multiArray2[0][0][0] << "\n";

	return 0;
}

int TestFuncBasic(int arg1, int arg2)
{
	return arg1 + arg2;
}

void TestFuncPointer(int arg1, int* arg2)
{
	*arg2 = arg1 + 100;
}

void TestFuncReference(int arg1, int& arg2)
{
	arg2 = arg1 + 100;
}

void TestFuncArray(char arg[])
{
	arg[7] = 'e';
}

void TestFuncMultiArray(int arg1[][2], int arg2[][2][2])
{
	arg1[0][0] = 2;
	arg2[0][0][0] = 2;
}
함수에 인자를 전달함에 있어 메모리가 어떻게 운영되는지 유념할 필요가 있다.
Ex1>방식의 경우 전달 하고자하는 인자와 함수에서 전달받은 인자를 저장하는 부분에서 메모리를 2배로 사용하게 되어 성능상의 불리한 점이 있다.
다음 그림을 참고하도록 한다.

Ex1>

function1

* main에서는 valueBasic1, valueBasic2, valueBasicReturn 세개의 값이 메모리를 차지하고 있다.
* TestFuncBasic를 호출하면 arg1, arg2가 메모리에 올려지고 계산된 값을 반환함과 동시에 소멸된다.

Ex2>

function2

* main에서는 valueBasic1, *valueBasic2, valueBasicReturn 세개의 값이 메모리를 차지하고 있다.
* 포인터변수 *valueBasic2는 valueBasicReturn의 주소값을 가지고 있다.
* 함수를 호출하면 전달된 포인터변수가 가리키는 값에 계산결과를 넣는다.

[C++ 정리] reference(참조) 의 사용 2015-06-12

포인터 변수에 주소값을 입력하기 위해서 &(ampersand)를 사용한 것과 마찬가지로 변수형으로 정의하여 사용할 수 있다.

#include "stdafx.h"
#include <iostream>

using namespace std;

int _tmain(int argc, _TCHAR* argv[])
{	
	int number = 100;

	// 참조변수 선언 및 초기화
	// ※ 반드시 변수를 정의할때 초기화해주어야 한다.
	int& referenceVariable = number;
		
	// 참조이기 때문에 같은 메모리를 사용하므로 하나를 변경하면 모두 변경된다고 봐야한다
	referenceVariable = 200;
	cout << "number :: " << number << "\n";
	cout << "reference :: " << referenceVariable << "\n";

	if (referenceVariable == number)
	{
		// referenceVariable는 메모리 상에 존재하지 않지만 number와 동일하다
		cout << "referenceVariable == number :: true \n";
	}

	const int& constVariable = number;
	// [Error] : 상수형으로 선언하면 변경할 수 없다.
	//constVariable = 100;
	// 상수를 변경할 수 없지만 참고하는 값을 변경하면 constVariable도 변경된다.
	number = 300;
	cout << "number :: " << number << "\n";
	cout << "reference :: " << constVariable << "\n";

	return 0;
}
* 참조변수 선언시 반드시 초기화 하여야 한다.
* 참조변수는 메모리상에 존재하지는 않지만 같은 메모리를 사용한다.

[C++ 정리] 구조체 / 공용체 / 열거체 2015-06-12

데이터를 효과적으로 변수에 담기위해 구조체 / 공용체 / 열거체를 사용한다.

#include "stdafx.h"
#include <iostream>

using namespace std;

// 구조체 선언
struct structSample
{
	char name[10];
	int number;
};

// 공용체 선언
union unionSample
{	
	int number1;
	void* number2;
};

// 열거체 선언
enum {GOOGLE, KAKAO, NAVER};

// 구조체 + 열거체
enum PAY_METHOD { GOOGLE_PAY, KAKAO_PAY, NAVER_PAY };
struct userInfo{
	PAY_METHOD payMethod;
	char name[10];
};

int _tmain(int argc, _TCHAR* argv[])
{	
	// Ex1> 구조체 사용
	structSample userA = {"opendocs1", 100};
	cout << "Ex1 :: " << userA.name << " // " << userA.number << "\n";

	// Ex2> 공용체 사용
	unionSample userB;
	// - 모든 멤버가 같은 메모리 공간을 차지하고 있어 한개의 값만 바꿔도 모두 변경된다.
	userB.number1 = 200;
	cout << "Ex2 :: " << userB.number1 << " // " << (int)userB.number2 << "\n";

	// Ex3> 열거체 사용
	// - 전역에서 사용되는 상수를 정의하여 사용할 수 있다.
	userInfo userC = { KAKAO_PAY, "opendocs2" };
	cout << "Ex3 :: " << userC.payMethod << " // " << userC.name << "\n";

	return 0;
}
* 가장 많이 사용되는 구조체는 여러 유형의 데이터를 그룹으로 많들어 한개의 객체처럼인식하고 프로그래밍 할 수 있도록 한다.
* 공용체는 거의 사용되지 않으나 모든 멤버가 같은 메모리 공간을 차지하고 있다는 특징이 있다
* 데이터의 유형을 전역에서 효과적으로 분기하고 명시적인 프로그래밍을 하기위해서 열거체가 사용된다.