0. 생성한 스크립트
- Function : Move함수 만들어서 버튼 안눌러도 오브젝트 이동되게 하기
- Movement : 버튼을 눌러서 오브젝트 이동시키기
- Overloading : 같은 이름의 함수를 만들어서 숫자 패드를 눌러 오브젝트 이동시키기
- Out : 실행하는 함수가 지역변수에 값을 집어넣기
- Reference : 함수로 지역변수에 값 집어넣기
- Params : 상대경로 주소와 절대경로 주소 출력하기
1. 함수
- 객체지향에서 함수는 매서드(Method)라는 이름으로 사용된다.
- 함수는 기능(연산)을 작성한 프로그램 코드이다.
- 함수의 호출 : 정의된 함수의 기능을 원하는 곳에서 사용한다는 뜻 입니다.
- 함수를 호출하면 스택에 저장되고 호출 종료시에는 호출한 곳으로 결과를 반환합니다.
2. x이동 함수
- 함수위에 /// : 어떤 역할을 하는 함수인지 적는 주석양식이 자동으로 써진다. (써놓으면 프로젝트 작업할때 혼동이 없다)
float xPosition = 0.0f;
xPosition = Move(2.0f); //호출부
print($"xPosition : {xPosition}");
Move(1.5f); //리턴값을 필요에따라 받지 않아도 된다.
float Move(float x) //정의부 : 어떻게 처리될지 정의하는 부분 / float x : 파라미터
{
transform.Translate(new Vector3(x, 0, 0));
print($"x방향으로 {x}만큼 이동");
return transform.position.x;
}

2. 열거형 자료형 - enum
- 열거형은 단어에 숫자를 부여해 명명된 상수 집합에 의해 정의되는 값 형식입니다.
- 즉, enum으로 선언된 변수로 안의 변수를 불러오면 변수가 선언된 순서대로 값이 매겨져 그 값이 가져오게된다.
- 이렇게 선언된 열거형은 비트 플래그로서 이진수를 정의한다면, 비트 논리 연산자(&, |)를 사용하여 선택적으로 교차할 수 있다.
3. 열거형 자료형을 이용한 오브젝트 이동
- 파라미터에 값이 안들어올때를 대비하여 디폴트 파라미터를 써 넣을수있는데 2번째 파라미터부터 쓸수있다.
- 3개 이상부터는 마지막부분에 디폴트 파라미터를 써야 오류를 막을 수 있다.
enum Direction
{
Forward = 0b_0000_0001, //0x01
Backward = 0b_0000_0010, //0x02
Right = 0b_0000_0100, //0x04
Left = 0b_0000_1000, //0x08
}
private void Update()
{
if (Input.GetKeyDown(KeyCode.W)) //1.0f
{
Move(Direction.Forward); //amounst는 안쓰니 디폴트값이 들어간다.
}
else if (Input.GetKeyDown(KeyCode.S)) //-1.0f
{
Move(Direction.Backward, -1.0f);
}
if (Input.GetKeyDown(KeyCode.D)) //1.5f
{
Move(Direction.Right, 1.5f);
}
else if (Input.GetKeyDown(KeyCode.A)) //-1.0f
{
Move(Direction.Left, -1.0f);
}
}
private void Move(Direction direction, float amount = 1.0f)
{
float x = 0.0f, z = 0.0f;
switch (direction)
{
case Direction.Forward:
case Direction.Backward:
{
z = amount;
}
break;
case Direction.Right:
case Direction.Left:
{
x = amount;
}
break;
}
print($"방향 : {direction.ToString()}");
print($"방향 : {(int)direction}");
transform.Translate(new Vector3(x, 0, z));
}
4. 동시입력 이동(대각선 이동)
- 비트값을 확인해서 1 이상이 나오는 방향으로 힘을 준다.
- 뚝뚝 끊겨서 한칸씩 이동한다.
enum Direction
{
Forward = 0b_0000_0001, //0x01
Backward = 0b_0000_0010, //0x02
Right = 0b_0000_0100, //0x04
Left = 0b_0000_1000, //0x08
}
uint direction = 0b_0000_0000;
if (Input.GetKeyDown(KeyCode.W))
{
direction |= (byte)Direction.Forward; //|연산으로 0001이 합해져서 direction으로 들어간다.
}
else if (Input.GetKeyDown(KeyCode.S))
{
direction |= (byte)Direction.Backward;
}
if (Input.GetKeyDown(KeyCode.D))
{
direction |= (byte)Direction.Right;
}
else if (Input.GetKeyDown(KeyCode.A))
{
direction |= (byte)Direction.Left;
}
MoveBit(direction);
void MoveBit(uint direction, float amount = 1.0f)
{
float x = 0.0f, z = 0.0f;
uint forward = direction & (uint)Direction.Forward;
if (forward > 0)
z = amount;
uint backward = direction & (uint)Direction.Backward;
if (backward > 0)
z = -amount;
uint right = direction & (uint)Direction.Right;
if (right > 0)
x = amount;
uint left = direction & (uint)Direction.Left;
if (left > 0)
x = -amount;
transform.Translate(new Vector3(x, 0, z));
}
5. S/W 역사
5-1 절차지향적 프로그래밍(기능) - 함수
- 루틴, 하위프로그램, 서브루틴, 메서드, 함수를 사용하는 함수형 프로그래밍 등을 절차 지향이라고 한다.(기능 중심)
- 어떤 기능을 제공해 줄 거냐를 중심으로 프로그래밍을 한다.
- 예를 들어, 이동할 거다, 숫자를 더할거다, 무엇을 할 것이다. 등등...
- 세월이 지나면서 기능보다 데이터가 더 중요해져 데이터 중심인 정보 공학적 프로그래밍으로 바뀌었다.
- 장점
- 1. 복사해서 붙이지 않고도 같은 코드를 다른 장소에서 다시 사용할 수 있게 해 준다.
- 2. GOTO문이나 JUMP문을 쓰는 것보다 프로그램의 흐름을 더 쉽게 따라갈 수 있게 해준다.
- 3. 모듈화를 하거나 구조화를 할 수 있다.
- 단점
- 1. 유지 보수가 어렵다. => 시간이 지날수록 함수가 쌓이고, 하나가 고장나면 시스템 전체가 고장난다.
- 2. 엄격하게 순서가 정해져 있어 비효율적이다.
5-2 정보공학(데이터) - 구조체
- 절차 지향 중심인 기능도 중요하지만 더 중요한건 데이터를 어떻게 저장할것이냐가 더 중요한 방법이라고 생각한 방식이다.
- 이때, '알고리즘'과 '자료구조'라는 학문이 탄생했다.
- 세월이 지나면서 함수가 커지고 이것을 편하게 수정하고 비용 절감을 위해서 점차 중요도가 바뀌게 되었다.
- 사람 대신 컴퓨터를 투입하면 일자리가 끊기게 되니 프로그래머들은 이 문제를 해결하기 위해 기능 중심과 데이터 중심을 하나로 합치기로 생각했다. => 객체지향 언어의 시작
5-3 객체지향적 프로그래밍(기능 + 데이터)
- 실생활에서 볼 수있는 오브젝트나 추상적인 개념들을 '객체'로 파악하여 객체간의 상호작용을 통해 프로그램을 개발하는 방식입니다.
- 객체지향 언어의 특징
- 1. 캡슐화
- 변수와 함수를 하나의 단위로 묶는 것을 의미한다.
- 대체로 클래스를 통해 구현되고, 해당 클래스의 인스턴스 생성을 통해 클래스 안에 포함된 멤버 변수와 메소드에 쉽게 접근할 수 있다.
- 내부 처리과정을 숨긴다는 의미가 있다.
- 2. 정보 은닉성
- 프로그램의 세부 구현을 외부로 드러나지 않도록 특정 모듈 내부로 감추는 것을 의미한다.
- 내부의 구현은 감추고 모듈 내에서의 응집도를 높이며, 외부로의 노출을 최소화하여 모듈 간의 결합도를 떨어뜨려 유연함과 유지보수성을 높이는 개념이다.
- 변수나 함수를 숨긴다는 의미가 있다.
- 접근 제한의 종류
- 1. public : 클래스의 외부에서 사용 가능하도록 노출시키는 것이다.
- 2. protected : 다른 클래스에게는 노출되지 않지만, 상속받은 자식 클래스에게는 노출되는 것이다.
- 3. private : 클래스의 내부에서만 사용되며 외부로 노출되지 않는다.
- 3. 상속성
- 자식 클래스가 부모 클래스의 특성과 기능을 그대로 물려받는 것을 말한다.
- 기능의 일부분을 변경해야 할 경우 자식 클래스에서 상속받은 그 기능만을 수정해서 다시 정의하게 되는데, 이러한 작업을 '오버라이딩'이라고 한다.
- 상속은 캡슐화를 유지하면서도 클래스의 재사용이 용이하도록 해 준다.
- 4. 추상화
- 여러 가지 사물이나 개념에서 공통되는 특성이나 속성 따위를 추출하여 구체적인 것은 감추고, 대략적이고 전체적인 그림만을 드러내어 클래스를 만들어내는 것을 의미한다.
- 이것을 이용하여 코드의 재 사용성, 가독성을 높이고 생산성의 증가, 에러 감소, 유지 보수에 있어 많은 시간을 줄일 수 있다.
- 추상화 종류
- 과정 추상화 : 수행 과정을 정의하지 않고, 전반적인 흐름만 파악할 수 있게 설계하는 방법 - 코드를 줄 단위가 아닌 함수 단위로 접근할 수 있게한다.
- 데이터 추상화 : 데이터의 세부적인 속성이나 용도를 정의하지 않고, 데이터 구조를 대표할 수 있는 표현으로 대체하는 것이다.
- 제어 추상화 : 이벤트 발생의 정확한 절차나 방법을 정의하지 않고, 대표할 수 있는 표현으로 대체하는 방법이다.
- 5. 다형성
- 하나의 변수, 또는 함수가 상황에 따라 다른 의미로 해석될 수 있는 것을 말한다.
- 서브타입 다형성 : 기초 클래스 또는 어떠한 인터페이스를 구현하는 상위 클래스를 생성하고, 해당 클래스를 상속받는 다수의 하위 클래스들을 만들어 상위 클래스의 포인터나 참조변수 등이 하위 클래스의 객체를 참조하게 하는 것이다.
- 이때 각각의 하위 클래스는 상위 클래스의 메소드 위에 자신의 메소드를 덮어쓰는 메소드 오버라이딩을 수행하며, 상위 클래스의 참조변수가 어떤 하위 클래스의 객체를 참조하느냐에 따라 호출되는 메소드가 달라진다.
- 임시 다형성
- 함수 오버로딩 : 동일한 이름의 함수를 매개변수에 따라 다른 기능으로 동작하도록 할 수 있다.
- 함수 오버로딩을 너무 많이 사용하면 전체적인 코드의 유지보수가 어려워지므로, 템플릿 또는 제네릭으로 대체하는 것이 일반적이다.
- 연산자 오버로딩 : 기본 연산자가 해당 클래스에 맞는 역할을 수행하게 하는 것이 가능하다.
- 함수 오버로딩 : 동일한 이름의 함수를 매개변수에 따라 다른 기능으로 동작하도록 할 수 있다.
- 강제 다형성
- 묵시적 형 변환
- 명시적 형 변환 : double a = (double)30;
- 1. 캡슐화
5-4 CBD (컴포넌트 기반 개발)
- 재사용이 가능한 컴포넌트의 개발 또는 상용 컴포넌트들을 조합하여 애플리케이션 개발 생산성과 품질을 높이고, 시스템 유지 보수 비용을 최소화할 수 있는 개발 방법 프로세스다.
- 컴포넌트 단위의 개발 및 조립을 통하여 정보시스템의 신속한 구축, 변경, 확장의 용이성과 타 시스템과의 호환성을 달성하고자 하는 소프트웨어 공학 프로세스다.

6. SDLC 생명주기
- 정보 시스템을 계획, 개발, 시험, 채용하는 과정을 뜻하는 용어다.
- 대개 요구사항 분석 -> 설계 -> 개발 -> 테스트 -> 운영 단계로 구성되어 있다.

7. 오버로딩
- 함수의 이름은 하나만 주고 매개변수를 다르게 함으로써 함수를 여러개 만드는 것을 말한다.
- 함수는 파라미터의 갯수나 종류가 다르면 같은 함수가 아니다.
- 파라미터의 종류나 갯수가 같으면 리턴타입이 달라도 같은 함수로 취급한다.
private void Update()
{
if (Input.GetKeyDown(KeyCode.Keypad1)) //Keypad1는 숫자 키패드 1이다.
Move(1.0f);
if (Input.GetKeyDown(KeyCode.Keypad2))
Move(new Vector2(1, 1));
if (Input.GetKeyDown(KeyCode.Keypad3))
Move(new Vector3(1, 1, 1));
}
private void Move(float x)
{
transform.Translate(new Vector3(x, 0, 0));
}
private void Move(Vector2 amount)
{
transform.Translate(new Vector3(amount.x, 0, amount.y));
}
private void Move(Vector3 amount)
{
transform.Translate(amount);
}
8. return 값 2개이상 받는 법 (Out 키워드)
- 변수를 참조 형태로 전달하는데 사용하고, 변수를 전달하기 전에 초기화 하지 않아도 되지만 반드시 메서드 안에서는 할당되어야한다. => int a;
- 매서드 내에서 전하는 변수를 초기화할 때 좋은 선택이다.
- 코드의 가독성을 높여주고 작성해야하는 코드는 양을 줄여준다.
- 메서드 내에서 반드시 할당해야하기 때문에 프로그래머가 실수하는 상황을 미연에 방지해준다.
- return은 돌려받을때 단 하나의 변수만 리턴 가능하다.
- 2개의 변수를 돌려받기 위해서는 out이라는 키워드를 사용한다.
int a = 10;
int b = 20;
int c;
Add(a, b, out c);
print($"{a} + {b} = {c}");
void Add(int val1, int val2, out int result)
{
result = val1 + val2;
}

9. 레퍼런스를 이용한 함수호출 (ref키워드)
- ref의 경우 변수를 참조 형태로 전달하는데 사용하고, 변수를 전달하기 전에 초기화가 반드시 되어 있어야 한다. => int a = 10;
- 메서드 내에서 전달하는 변수를 변경해야할 때 좋은 선택이다.
- 매개변수를 레퍼런스로 전달하기 때문에 성능 향상을 기대할 수 있다.
- 시간과 메모리를 절약한다.
- 기본적으로 함수를 실행해도 리턴을 하지 않으면 전역변수가 아닌 이상 값에 영향을 미치지 않는다.
- 하지만 지역변수에도 함수의 변화가 영향을 미치게 하여면 파라미터를 (ref int a)처럼 "ref"를 붙여서 함수 파라미터를 적는다.
- 호출도 swap(ref d, ref e);로 호출한다. => 평상시의 함수호출은 call by value 라고 부르지만 이런 호출은 call by reference라고 부른다.
int a = 10, b = 20;
print($"1 : {a}, 2 : {b}");
Swap(ref a, ref b);
print($"1 : {a}, 2 : {b}");
void Swap(ref int val1, ref int val2)
{
int temp = val1;
val1 = val2;
val2 = temp;
print($"1 : {val1}, 2 : {val2}");
}



10. 상대경로 / 절대경로
print(Application.dataPath); //에셋 폴더 경로가 출력된다. (상대경로 출력)
print(System.IO.Directory.GetCurrentDirectory()); //프로젝트폴더의 경로가 출력된다.(절대경로 출력)
- 기타 -
- assets 폴더 내에 같은 파일명의 meta 파일이 생성되는데 이거에 같은 파일명의 바꾼 설정들이 있어 삭제하면 안된다.
- 함수위에 참조는 이 함수에 어떤것이 참조되어있나를 나타내어 그것을 클릭하면 해당 위치로 이동한다.
- Unity 메시지 는 유니티 내부에서 자동으로 참조시키는 내용이다.