일 | 월 | 화 | 수 | 목 | 금 | 토 |
---|---|---|---|---|---|---|
1 | ||||||
2 | 3 | 4 | 5 | 6 | 7 | 8 |
9 | 10 | 11 | 12 | 13 | 14 | 15 |
16 | 17 | 18 | 19 | 20 | 21 | 22 |
23 | 24 | 25 | 26 | 27 | 28 |
- 다트 언어
- Flutter
- docker
- github
- 유니티
- 구조체
- c# 추상 클래스
- jupyter
- C언어 포인터
- jupyter lab
- Houdini
- c#
- 포인터
- 도커
- Unity
- C++
- 플러터
- HTML
- dart 언어
- Algorithm
- Python
- C# delegate
- 깃
- c언어
- vim
- git
- c# 윈폼
- Data Structure
- c# winform
- gitlab
- Today
- Total
목록분류 전체보기 (507)
nomad-programmer
대리자는 보통의 메소드뿐 아니라 일반화 메소드도 참조할 수 있다. 물론 이 경우에는 대리자도 일반화 메소드를 참조할 수 있도록 형식 매개 변수를 이용하여 선언되어야 한다. 형식 매개 변수를 이용해서 대리자를 선언하는 요령은 메소드와 같다. 괄호 사이에 형식 매개 변수를 넣어주면 된다. 일반화 대리자 예제 using System; namespace test { delegate int Compare(T a, T b); internal class Program { static int AscendCompare(T a, T b) where T: IComparable { return a.CompareTo(b); } static int DescendCompare(T a, T b) where T : IComparabl..
대리자와 이벤트 사건을 영어로는 이벤트(Event)라고 하는데, 컴퓨터에 발생하는 이벤트에 반응하도록 프로그램을 만드는 것을 일컬어 "이벤트 기반 프로그래밍(Event Driven Programming)" 이라고 부른다. 멀티 패러다임 언어인 C#이 지원하는 또 하나의 프로그래밍 패러다임인 셈이다. 이벤트 기반 프로그래밍은 GUI(Graphic User Interface) 를 만들 때 특히 유용하다. C#에서 지원하는 이벤트 기반 프로그래밍을 이해하려면 먼저 대리자를 알아야 하고 그 다음 이벤트를 알아야 한다. 2020/06/16 - [Programming/C] - [C] 함수 포인터 2020/06/16 - [Programming/C] - [C] 콜백 함수 2020/06/18 - [Programming/..
예외는 throw 문을 이용하여 던진다. 그래서 던진 예외를 try~catch로 받는다. throw 는 보통 문(statement)으로 사용하지만 C#7.0부터는 식(expression)으로도 사용할 수 있도록 개선되었다. int? foo = null; // foo는 null이므로 bar에 foo를 할당하지 않고 throw 식이 실행된다. int bar = foo ?? throw new ArgumentNullException(); // 조건 연산자 안에서도 사용할 수 있다. int[] array = new int[] {1, 2, 3}; int index = 4; // 삼항 연산자를 이용한 예외 던지기 int value = array[ index >= 0 && index < 3 ? index : throw..
foreach를 사용할 수 있는 클래스를 만드려면 IEnumerable 인터페이스와 IEnumerator 인터페이스를 상속하고 이들에게 선언되어 있는 메소드와 프로퍼티를 구현해야 한다. 일반화 클래스도 IEnumerable과 IEnumerator 인터페이스를 상속하여 이들의 메소드와 프로퍼티를 구현하면 일반은 foreach를 통해 순회를 할 수 있지만, 요소를 순회할 때마다 형식 변환을 수행하는 오버로드가 발생한다는 문제가 있다. 성능을 위하여 기껏 일반화를 통해 형식 변환을 제거하였더니 foreach 구문에서 형식 변환을 일으켜 성능을 저하시키면 너무 바보 같은 일일것이다. System.Collections.Generic 네임스페이스에는 이 문제를 풀 수 있는 열쇠를 가지고 있다. 바로 IEnumera..
System.Collections 의 컬렉션들은 어떤 형식이든 object 형식으로 상속받고 있으므로 object 형식으로 형식 변환이 가능하다. 이것은 바로 이점을 활용하기 위해 만들어진 자료 구조이다. 컬렉션 객체에 int 형 데이터, string 형 데이터, FooClass 의 객체도 담을 수 있다. 하지만 컬렉션은 object 형식에 기반하고 있기 때문에 태생적으로 성능 문제를 안고 있다. 컬렉션의 요소에 접근할 때마다 형식 변환이 주구장창 일어나기 때문이다. "일반화 컬렉션 (System.Collections.Generic)" 은 object 형식 기반의 컬렉션이 갖고 있던 문제를 말끔히 해결한다. 일반화 컬렉션은 말 그대로 일반화에 기반해서 만들어져 있기 때문에 컴파일할 때 컬렉션에서 사용할 ..
일반화 메소드나 일반화 클래스가 입력받는 형식 매개 변수 T는 "모든" 데이터 형식을 대신할 수 있다. 이렇게 모든 형식에 대응할 수 있는 형식 매개 변수가 필요한 때도 있지만, 종종 특정 조건을 갖춘 형식에만 대응하는 형식 매개 변수가 필요할 때도 있다. 이 때 형식 매개 변수의 조건에 제약을 줄 수 있다. 예를 들어 MyList 클래스의 형식 매개 변수 T에 "MyClass 로부터 상속받는 형식이어야 할 것" 이라는 제약을 주면 다음과 같이 클래스 선언문의 헤더에 where 절을 추가해주면 된다. class MyList where T : MyClass { // ... } 일반화 메소드도 비슷하다. CopyArray() 의 형식 매개 변수 T에 "값 형식이어야 할 것" 이라는 제약은 다음과 같이 줄 수..
C++ 언어에서의 "템플릿 (Template)" 이라고 생각하면 된다. template C#은 프로그래머가 작성한 하나의 코드가 여러 가지 데이터 형식에 맞춰 동작할 수 있도록 "일반환 프로그래밍" 을 지원한다. 일반환 프로그래밍은 코드 생산성을 좌우하는 아주 중요한 요소이며 일반화 컬렉션은 반드시 익혀둘 필요가 충분하다. 특수한 개념으로부터 공통된 개념을 찾아 묶는 것을 "일반화 (Generalization)" 라고 한다. "일반화 프로그래밍 (Generic Programming) " 은 이러한 일반화를 이용하는 프로그래밍 기법이다. 일반화하는 대상은 "데이터 형식 (Data Type)" 이다. void CopyArray( int[] source, int[] target) { for(int i=0; i..
https://asciinema.org/ asciinema - Record and share your terminal sessions, the right way Copy & paste Any time you see a command you'd like to try in your own terminal just pause the player and copy-paste the content you want. It's just a text after all! asciinema.org 아스키네마로 녹화해서 아스키네마 서버에 올린 것을 svg 애니메이션 파일로 추출한다. 그래서 이것을 github 같은 곳에 올릴 때 추가하면 무한 반복 자동 재생 애니메이션으로 사용할 수 있다. https://github.com/..
인덱서(Indexer) 는 인덱스(Index) 를 이용해서 객체 내의 데이터에 접근하게 해주는 프로퍼티라고 생각하면 된다. 객체를 마치 배열처럼 사용할 수 있게 해준다. 인덱서를 선언하는 형식은 다음과 같다. class 클래스이름 { // 인덱스의 식별자가 꼭 index라는 이름일 필요는 없다. 한정자 인덱서형식 this[형식 index] { get { // index를 이용하여 내부 데이터 반환 } set { // index를 이용하여 내부 데이터 저장 } } } 인덱서는 프로퍼티처럼 식별자(변수 이름) 를 따로 가지지 않는다. 프로퍼티가 이름을 통해 객체 내의 데이터에 접근하게 해준다면, 인덱서는 인덱스를 통해 객체 내의 데이터에 접근하게 해준다. using System; using System.Co..
컬렉션이란, 같은 성격을 띄는 데이터의 모음을 담는 자료 구조를 말한다. 배열도 .NET Framework가 제공하는 다양한 컬렉션 자료 구조의 일부이다. .NET Framework의 여타 컬렉션들이 상속하게 되어 있는 ICollection 인터페이스를 상속함으로써 System.Array 클래스 자신이 컬렉션의 일원임을 증명하고 있다. public abstract class Array : ICloneable, IList, ICollection, IEnumerable .NET Framework는 배열 말고도 여러 컬렉션 클래스들을 제공한다. ArrayList (자료 구조에서의 Linked List, Python에서는 list) Queue (Python에서 Queue 모듈) Stack (Python에서 li..
2차원 배열이나 3차원 배열 같은 다차원 배열을 "배열을 요소로 갖는 배열" 이다. 허나 진정한 의미에서의 배열을 요소로 갖는 배열은 "가변 배열 (Jagged Array)" 이다. 가변 배열은 다양한 길이의 배열을 요소로 가지는 다차원 배열로 이용될 수 있다. 2차원 배열의 요소에 접근할 때 반드시 첨자 두 개를 사용해야 했다. 하나만 사용해서 1차원 배열에 접근한다거나 하는 일은 불가능하다. 아래의 예를 보자. int[,] arr2d = new int[2, 3] { {1, 2, 3}, {4, 5, 6} }; // 2차원 배열이면 첨자 2개가 필히 들어가야 한다. arr2d[1, 2]; // 2차원 배열이면 첨자가 1개 뿐이라면 에러 발생. 1차원 배열에 접근할 수 없다... arr2d[1]; 가변 배..
다차원 배열이란 차원이 둘 이상인 배열을 말한다. 2차원 배열도 다차원 배열에 해당한다. using System; namespace test { internal class Program { public static void Main(string[] args) { int[,,] arr3d = new int[4, 3, 2] { { {0, 1}, {2, 3}, {4, 5} }, { {6, 7}, {8, 9}, {10, 11} }, { {12, 13}, {14, 15}, {16, 17} }, { {18, 19}, {20, 21}, {22, 23} } }; for (int i = 0; i < arr3d.GetLength(0); i++) { for (int j = 0; j < arr3d.GetLength(1); j..
C#에서는 모든 것이 객체이다. 배열도 객체이며 당연히 기반이 되는 형식이 있다. .NET Framework의 CTS (Common Type System) 에서 배열은 System.Array 클래스에 대응된다. 따라서 System.Array의 특성과 메소드를 파악하면 배열의 특성과 메소드를 알게 되는 셈이다. Array 클래스의 주요 메소드와 프로퍼티 분류 이름 설명 정적 메소드 Sort() 배열을 정렬한다. BinarySearch() 이진 탐색을 수행한다. IndexOf() 배열에서 찾고자 하는 특정 데이터의 인덱스를 반환한다. TrueForAll() 배열의 모드 요소가 지정한 조건에 부합하는지의 여부를 반환한다. FindIndex() 배열에서 지정한 조건에 부합하는 첫 번째 요소의 인덱스를 반환한다...
추상 클래스는 클래스처럼 구현된 프로퍼티를 가질 수도 있는 한편, 인터페이스처럼 구현되지 않은 프로퍼티도 가질 수 있다. 추상 클래스에서는 이것을 "추상 프로퍼티 (Abstract Property)" 라고 한다. 추상 메소드가 그랬던 것처럼, 추상 프로퍼티 역시 인터페이스의 프로퍼티와 다를 것이 없다. 파생 클래스가 해당 프로퍼티를 구현하도록 강제하는 것일 뿐이다. 추상 프로퍼티는 인터페이스처럼 구현을 비워놓은 것만으로는 추상 프로퍼티를 만들 수 없다. 그리하면 C# 컴파일러가 자동 구현 프로퍼티로 간주하고 구현을 자동으로 채워 넣을 것이다. 그래서 추상 프로퍼티는 abstract 한정자를 이용하여 선언한다. abstract class 추상 클래스이름 { abstract 데이터형식 프로퍼티이름 { get..
인터페이스는 메소드뿐만 아니라 프로퍼티와 인덱서도 가질 수 있다. 프로퍼티나 인덱서를 가진 인터페이스를 상속하는 클래스가 반드시 해당 프로퍼티와 인덱서를 구현해야 하는 것은 물론이다. 당연한 이야기지만 인터페이스에 들어가는 프로퍼티는 구현을 갖지 않는다. 인터페이스의 프로퍼티 선언이 클라스의 자동 구현 프ㅗ퍼티 선언과 그 모습이 동일하다. 다음은 인터페이스의 프로퍼티 선언 형식이다. interface 인터페이스이름 { public 형식 프로퍼티1 { get; set; } public 형식 프로퍼티2 { get; set; } } 다음은 프로퍼티를 갖고 있는 인터페이스와 이를 상속하는 파생 클래스의 예이다. interface INameInfo { string Name { get; set; } } class ..
이름이 없는 형식, 즉 "무명 형식 (Anonymous Type)" 의 프로퍼티를 정의할 수 있다. 무명 형식은 형식의 선언과 동시에 인스턴스를 할당한다. 이 때문에 인스턴스를 만들고 다시는 사용하지 않을 때 요기하게 쓰인다. // 괄호 사이에 임의의 프로퍼티 이름을 적고 값을 할당하면 그대로 새 형식의 프로퍼티가 된다. var myInstance = new { Name = "test", Age = 17 }; Console.WriteLine( myInstance.Name, myInstance.Age ); 무명 형식에는 주의할 점이 있다. 그것은 무명 형식의 프로퍼티에 할당된 값은 변경 불가라는 점이다. 한마디로 한번 무명 형식의 인스턴스가 만들어지고 난 다음에는 읽기만 할 수 있다는 것이다. 이러한 특징..
프로퍼티를 이용한 초기화는 다음과 같다. 클래스이름 인스턴스 = new 클래스이름() { 프로퍼티1 = 값, 프로퍼티2 = 값, 프로퍼티3 = 값 } 객체를 생성할 때 목록에 객체의 모든 프로퍼티가 올 필요는 없다. 초기화하고 싶은 프로퍼티만 넣어서 초기화하면 된다. 매개 변수가 있는 생성자를 작성할 때와는 달리 어떤 필드를 생성자 안에서 초기화할지를 미리 고민할 필요가 없다. using System; namespace CSharpExample { class MainApp { class BirthdayInfo { public string Name { get; set; } public DateTime Birthday { get; set; } public int Age { get { return new Da..
// home brew 설치/usr/bin/ruby -e "$(curl -fsSL https://raw.githubusercontent.com/Homebrew/install/master/install)"iTerm2 설치https://www.iterm2.com/ iTerm2 - macOS Terminal ReplacementiTerm2 by George Nachman. Website by Matthew Freeman, George Nachman, and James A. Rosen. Website updated and optimized by HexBrainwww.iterm2.com위의 링크로 가서 다운로드 후 설치한다.iTerm2 테마 설정환경 설정 - Profiles - Colors표시된 저곳을 클릭하여 ..
프로퍼티는 데이터의 오염에 대해선 메소드처럼 안전하고, 데이터를 다룰 때는 필드처럼 간결하다. 하지만 많은 경우 중복된 코드를 작성하고 있다는 기분이 들게 된다. 다음 코드의 NameCard 클래스를 보면 Name과 PhoneNumber 프로퍼티는 단순히 name과 phoneNumber 필드를 읽고 쓰기만 하고 있다. 여기에는 아무 논리도 섞여 있지 않다. 이런 경우 C# 언어는 더 단순하게 만드는 "자동 구현 프로퍼티 (Auto-Implemented Property)" 를 C# 3.0 때 도입했다. public class NameCard { private string name; private string phoneNumber; public string Name { get { return name; } ..
* Python의 property, setter 데코레이션과 똑같다고 생각하면 된다. 객체 지향 언어라면 모름지기 "은닉성"을 표현할 수 있어야 한다. 객체의 데이터가 의도하지 않게 오염되는 것을 방지해야 하니까. C++나 Java에서는 private과 protected 접근 한정자를 이용해서 클래스 내의 필드를 외부에서 보이지 않게 감추고, 이 필드에 접근하는 메소드들을 public으로 따로 제공한다. C# 언어도 이 방법을 그대로 사용할 수 있지만, C# 언어는 이보다 더 우아한 장치를 제공한다. 그것이 바로 프로퍼티(Property)이다. 프로퍼티를 이용하는 이유? 은닉성과 편의성 예를 들어 다음과 같은 클래스가 있다고 해보자. 이 클래스는 int 형식 myField를 private로 갖고 있다. ..