2019.03.22 과제
카테고리 없음 2019. 3. 22. 20:57for문
https://docs.microsoft.com/ko-kr/dotnet/csharp/language-reference/keywords/for
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 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 | using System; using System.Collections.Generic; using System.Linq; using System.Text; namespace Study_00 { class Test { public Test() { //생성자 for (int i = 0; i < 2; i++) { Console.WriteLine(i+5); } //int i의 값은 0이다. //i의 값은 0이다. //0은 2보다 작다 //비교 연산된 값은 True다. //비교 연산된 값이 True이므로 본문을 실행 한다. //i의 값은 0이다. //+ 연산된 값은 5이다. //5를 출력하고 줄바꿈한다. //iterator섹션을 실행 한다. //i의 값은 0이다. //++연산된 값은 1이다. //condition 섹션을 실행 한다. //i의 값은 1이다. //1은 2보다 작다. //비교연산된 값은 True다. //비교 연산된 값이 True이므로 본문을 실행 한다. //i의 값은 1이다. //+ 연산된 값은 6이다. //6을 출력하고 줄바꿈 한다. //iterator섹션을 실행 한다. //i의 값은 1이다. //++연산된 값은 2이다. //condition 섹션을 실행 한다. //i의 값은 2이다. //2은 2보다 작다. //비교연산된 값은 Flase다. //비교 연산된 값이 False이므로 루프를 종료 한다. Console.ReadKey(); } } } | cs |
값형식: https://docs.microsoft.com/ko-kr/dotnet/csharp/language-reference/keywords/value-types
값현식의 변수에 새 값을 할당하면 해당값이 복사 된다.
모든 값 형식은 System.ValueType 에서 암시적 파생된다.
값형식 변수는 기본적으로 null일수없다. 그러나 해당 nullable 형식의 변수는 null 일수 있다.
값형식에는 해당 형식의 기본값을 초기화 하는 암시적 기본 생성자가 있다.
기본값표 : https://docs.microsoft.com/ko-kr/dotnet/csharp/language-reference/keywords/default-values-table
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 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 | using System; using System.Collections.Generic; using System.Linq; using System.Text; namespace Study_00 { class Test { public Test() { //Test클래스의 생성자 //값형식의 초기화 //지역변수는 사용하기 전에 초기화 해야 한다. //다음과 같이 초기화 하지 않고 지역변수를 선언할수 있다. int myInt; //초기화 전에 사용할수 없다. //초기화 하기 전에 사용하면 다음과 같은 에러를 만들어 낸다. //[ERROR] 할당되지 않은 'myInt'지역변수를 사용했습니다. //Console.WriteLine(myInt); //다음과 같이 초기화 할수 있다. myInt = new int(); Console.WriteLine(myInt); //이것은 다음 문과 같다. myInt = 0; Console.WriteLine(myInt); //다음과 같이 선언과 초기화를 동일한 문에 포함 할수 있다. int myInt2 = new int(); //또는 int myInt3 = 0; //new 연산자를 사용하면 특정 형식의 기본 생성자가 호출되고 //변수에 기본값이 할당 된다. //기본 생성자가 0값을 myInt에 할당 했다. Console.ReadKey(); } } } | cs |
참조형식 : https://docs.microsoft.com/ko-kr/dotnet/csharp/language-reference/keywords/reference-types
C#형식은 참조형식과 값형식 두가지가 있다.
참조형식의 변수에 데이터(개체)에 대한 참조가 저장된다.
참조형식에는 두가지 변수가 같은 개체를 참조할수 있으므로
한 변수에 대한 작업이 다른 변수에서 참조하는 개체에 영향을 미칠수 있다.
다음 키워드는 참조형식을 선언하는데 사용된다.
class, interface, delegate
다음과 같은 기본 참조형식도 제공한다.
dynamic, object, string
스택과 힙
값 형식 : int
부호있는 32비트 정수
https://docs.microsoft.com/ko-kr/dotnet/csharp/language-reference/keywords/int
범위 : -21억 ~ 21억
리터럴?
컴퓨터 과학 분야에서 리터럴(literal)이란 소스 코드의 고정된 값을 대표하는 용어다.
https://ko.wikipedia.org/wiki/%EB%A6%AC%ED%84%B0%EB%9F%B4
리터럴은 데이터 그 자체를 뜻 한다.
변수에 넣는 변하지 않는 데이터를 의미하는 것이다.
변수및 상수에 저장되는 값 자체
https://vitalholic.tistory.com/15
리터럴이란, 컴파일시 프로그램 내에 정의되어 있는 그대로 정확히 해석되어야 할 값을 의미한다.
리터럴은 숫자 뿐 아니라, 문자 또는 문자열일 수 있다.
http://www.terms.co.kr/literal.htm
예) x = 7
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 29 30 31 32 33 34 35 | using System; using System.Collections.Generic; using System.Linq; using System.Text; namespace Study_00 { class Test { public Test() { //Test클래스의 생성자 //10진수 리터럴로 표현된 90,964와 같은 정수가 int 값에 할당된다. //10진수 리터럴에는 접두사가 없다. int intValue1 = 90946; //16진수 리터럴로 표현된 0x16342 //0x 또는 0X 접두사를 사용하여 16진수 리터럴을 나타낸다. int intValue2 = 0x16342; //2진 리터럴 0b0001_0110_0011_0100_0010 //0b 또는 0B 접두사를 사용하여 이진 리터럴을 나타낸다. //2진수 계산기 : https://ko.calcuworld.com/%EC%88%98%ED%95%99/2%EC%A7%84%EB%B2%95-%EA%B3%84%EC%82%B0%EA%B8%B0/ int intValue3 = 0b0001_0110_0011_0100_0010; Console.WriteLine("10진수 리터럴 : " + intValue1); Console.WriteLine("16진수 리터럴 : " + intValue2); Console.WriteLine("2진 리터럴 : " + intValue3); Console.ReadKey(); } } } | cs |
이어서 할것..
float: 32비트 부동소수점 값을 저장하는 단순 형식
https://docs.microsoft.com/ko-kr/dotnet/csharp/language-reference/keywords/float
부동 소수점 형식 표 (float, double, decimal)
기본적으로 대입연산자 오른쪽의 실수 리터럴은 double로 처리 됨.
변환
식에서 숫자 정수 형식과 부동 소수점 형식을 함께 사용할 수 있다.
이 경우 정수 형식이 부동 소수점 형식으로 변환됨.
식의 계산은 다음 규칙에 따라 수행됨.
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 29 | using System; using System.Collections.Generic; using System.Linq; using System.Text; using System.Threading; namespace Study_00 { class Test { public Test() { //int, short및 float가 수학식에 포함되어 float 결과를 제공 //float 은 System.Single형식의 별칭 이다. int x = 3; float y = 4.5f; short z = 5; var result = x * y / z; Console.WriteLine("The result is {0}", result); Type type = result.GetType(); Console.WriteLine("result is of type : {0}", type.ToString()); Console.ReadKey(); } } } | cs |
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 | using System; using System.Collections.Generic; using System.Linq; using System.Text; using System.Threading; namespace Study_00 { class Test { public Test() { int monsterHp; int monsterMaxHp = 120; monsterHp = monsterMaxHp; Console.WriteLine("몬스터 체력 : ({0}/{1})", monsterHp, monsterMaxHp); Console.ReadKey(); } } } | cs |
Floating Point Number의 진실 in C#
long :
https://docs.microsoft.com/ko-kr/dotnet/csharp/language-reference/keywords/long
long은 다음표에 나와있는 크기와 범위에 따라 값을 저장하는 정수형식을 나타냄
범위 : –9,223,372,036,854,775,808 ~ 9,223,372,036,854,775,807
부호있는 64비트 정수
리터럴
10진수 리터럴, 16진수 리터럴 또는 이진 리터럴을 할당하여 long변수를 선언하고 초기화 할수 있다.
0x또는 0X접두사를 사용하여 16진수 리터럴을 나타내고
0b또는 0B접두사를 사용하여 이진 리터럴을 나타낸다.
10진수 리터럴에는 접두사가 없다.
소문자 l 을 접미사로 사용할수있다.
구별을 위해 L을 사용하자.
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 29 | using System; using System.Collections.Generic; using System.Linq; using System.Runtime.InteropServices; using System.Text; namespace Study_00 { class Test { public Test() { long a = Int64.MaxValue; a += 1; //가장 작은 수가 되어 버렸다. //–9,223,372,036,854,775,808 ~ 9,223,372,036,854,775,807 Console.WriteLine(a); //-9223372036854775808 //4294967296는 uint범위를 초과하기 때문에 long형식이다. var longVal1 = 4_294_967_296; //long에서 float, double또는 decimal은 미리 정의된 암시적 변환이 있으나 //없는 경우 캐스트 해야 한다. int x = (int)8L; } } } | cs |
double :
https://docs.microsoft.com/ko-kr/dotnet/csharp/language-reference/keywords/double
double 키워드는 64비트 부동 소수점 값을 저장하는 단순 형식이다.
근사범위를 가진다. : ±5.0 × 10−324 ~ ±1.7 × 10308
전체 자릿수 : ~15-17개
.NET형식 : System.Double
리터럴
기본적으로 대입 연산자 오른쪽의 실수 리터럴은 double로 처리 된다.
그러나 정수가 double로 처리 되도록 하려면 접미사 d 또는 D를 사용하면 된다.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 | using System; using System.Collections.Generic; using System.Linq; using System.Runtime.InteropServices; using System.Text; namespace Study_00 { class Test { public Test() { int x = 3; float y = 4.5f; short z = 5; double w = 1.7E+3; Console.WriteLine($"x:{x} y:{y} z:{z} w:{w}"); } } } | cs |
char : https://docs.microsoft.com/ko-kr/dotnet/csharp/language-reference/keywords/char
char 키워드는 .NET Framework에서 유니코드 문자를 표현하는데 사용하는 Sytstem.Char 구조체의 인스턴스를 선언하는데 사용된다.
Char 개체의 값은 16비트 숫자(서수)값이다.
서수 : 순서를 나타내는 수의 쓰임방식이다.
리터럴
char 형식의 상수는 문자 리터럴, 16진수 이스케이프 시퀀스 또는 유니코드 표현으로 기록 될수 있다.
정수 문자 코드를 캐스트 할수도 있다.
ex ) char[] chars = new char[4];
char[0] = (char)88
실습
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 | using System; using System.Collections.Generic; using System.Linq; using System.Runtime.InteropServices; using System.Text; namespace Study_00 { class Test { public Test() { char[] chars = new char[4]; chars[0] = 'X'; chars[1] = '\x0058'; chars[2] = (char) 88; chars[3] = '\u0058'; foreach (char c in chars) { Console.WriteLine(c + " "); } } } } | cs |
https://www.utf8-chartable.de/unicode-utf8-table.pl
아스키코드 (ASCII)
미국 ANSI에서 표준화 한 정보교환용 7비트 부호체계 (128개)
문자와 기호가 해당 숫자 표현으로 변환되어야 하는 필요
데이터 저장과 교환가능 해짐
아스키코드를 이용해 다른언어를 표현하기에 7비트로는 부족했기에 8비트로 확장한 아스키코드가 나옴
이를 ANSI코드라 부름
2의 7승 : 128개 -> 2의 8승 : 256개로 128개나 더 쓸수 있게 됨
위키 : https://ko.wikipedia.org/wiki/ASCII
참고 : https://minwan1.github.io/2018/06/09/2018-06-09-ASCII-Unicode/
유니코드 (Unicode)
위키 : https://en.wikipedia.org/wiki/Unicode
참고 : https://whatisthenext.tistory.com/103
전세계의 모든 문자를 컴퓨터에서 일관되게 표현하고 다룰수있도록 설계된 산업 표준.
한글은 자음+모음의 조합이 128개가 넘음
중국어 한자의 개수가 만개가 넘음 아스키로는 불가능
그래서 용량을 확장한 2byte (2의 16승 : 65536)의 유니코드가 등장
유니코드는 총 110만개가 넘는 코드를 지정할수 있음
문자 인코딩
특정한 문자 집합 안의 문자들을 컴퓨터에서 사용하기 위해 일정한 범위 안의 정수(코드값)으로 변환하는 방법
유니코드 포인트를 8비트 숫자의 집합으로 나타내는 UTF-8이나 16비트의 숫자 집합으로 나타내는 UTF-16이 포함됨
문자열 string : https://docs.microsoft.com/ko-kr/dotnet/csharp/programming-guide/strings/
문자열 값은 텍스트인 String 형식의 개체
내부적으로 텍스트는 Char 개체의 순차적 읽기전용 컬렉션 (배열) 로 저장됨
문자열 끝에 null 종료 문자가 없으므로 C# 문자열에는 포함된 null문자 ('\0')를 여러개 사용할수 있다.
문자열의 Length속성은 유니코드 문자 수가 아닌 포함된 char 개체수를 나타냄
문자열에 개별 유니코드 코드 포인트에 엑세스 하려면 StringInfo개체를 사용
문자열과 System.String
C#에서 string 키워드는 String의 별칭
String 클래스는 문자열을 안전하게 작성, 조작및 비교 할수 있도록 다양한 메서드를 제공
null : https://docs.microsoft.com/ko-kr/dotnet/csharp/language-reference/keywords/null
null 키워드는 개체를 참조 하지 않는 null참조를 나타내는 리터럴
null은 참조형식 변수의 기본값
일반적인 값형식은 null일수 없다.
그러나 nullable 값형식이 도입 됨. (c#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 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 | using System; using System.Collections.Generic; using System.Linq; using System.Runtime.InteropServices; using System.Text; namespace Study_00 { class Test { public Test() { //초기화 없이 선언 string message1; //null값으로 초기화 string message2 = null; //비어 있는 문자열로 초기화 //"" 리터럴 대신 Empty상수를 이용함 string message3 = System.String.Empty; //보통의 문자열 리터럴 ""로 묶음 string oldPath = "c:\\Program Files\\Microsoft Visual Studio 8.0"; //축어적 문자열 리터럴 @을 사용 string newPath = @"c:\Program Files\Microsoft Visual Studio 9.0"; //명시적으로 네임스페이스 선언하여 사용할수도 있음 System.String greeting = "Hello World!"; //지역변수 var 타입을 사용할수도 있음 (암시적으로 변환, 컴파일 타임에 ) var temp = "반갑습니다."; //상수 값으로 사용도 가능 const string message4 = "문자열은 너무 공부할게 많다..."; //new 키워드를 사용하여 String 클래스의 인스턴스를 생성할수있으며 //생성자를 사용하여 문자 배열을 매개변수로 전달 할수도 있다. char[] letters = { 'A', 'B', 'C' }; string alphabet = new string(letters); //문자 배열이 포함된 문자열을 초기화할 경우를 제외하고는 문자열 개체를 만들기 위해 new 연산자를 사용하지 않습니다. } } } | cs |
문자열표현식 (문자열보간)
$특수 문자는 문자열 리터럴을 보간된 문자열로 식별한다.
보간된 문자열은 보간된 식이 포함될 수 있는 문자열 리터럴이다.
보간된 문자열이 결과 문자열로 해석되면 보간된 식이 있는 항목이 식 결과의 문자열 표현으로 바뀐다.
C# 6 이상 버전에서 사용할 수 있음.
예제는 몬스터 잡기에서 사용했습니다.
https://docs.microsoft.com/ko-kr/dotnet/csharp/language-reference/tokens/interpolated
몬스터 잡기 (1~3차까지)
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 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 | using System; using System.Collections.Generic; using System.Linq; using System.Text; using System.Threading; namespace Study_00 { class Test { string monsterName = "오우거"; int maxMonsterHp = 123; int monsterHp; string monsterDesc = "몬스터는 사납고 무섭습니다."; string heroName = "홍길동"; int maxHeroHp = 80; int heroHp; int heroAttackDamage = 4; public Test() { //Test클래스의 생성자 this.monsterHp = this.maxMonsterHp; this.heroHp = this.maxHeroHp; Log($"몬스터의 이름은 {monsterName} 입니다."); Log($"몬스터의 체력은 {monsterHp}/{maxMonsterHp}입니다."); Log(monsterDesc); Log($"용사의 이름은 {heroName} 입니다."); Log($"용사의 공격력은 {heroAttackDamage} 입니다."); AttackMonster(); while (true) { if (monsterHp <= 0) break; Log($"공격을 더 하시겠습니까? (Y/N)", false); var info = Console.ReadKey(); Log(""); if (info.Key == ConsoleKey.Y) { Log($"몇회 공격하시겠습니까?", false); int attackCnt; Int32.TryParse(Console.ReadLine(), out attackCnt); this.ClearCurrentConsoleLine(); if (attackCnt > 0) { Log($"{attackCnt}회 공격을 시도 합니다."); for (int i = 0; i < attackCnt; i++) { this.AttackMonster(); if(this.monsterHp <= 0) break; Thread.Sleep(300); } } else { Log($"잘못된 횟수입니다."); continue; } } else if (info.Key == ConsoleKey.N) { break; } else { Log("잘못된 선택입니다."); } } Log("프로그램을 종료 합니다."); Console.ReadKey(); } private void AttackMonster() { Log($"용사몬스터를 공격했습니다."); Log("몬스터는 ", false); WriteLineWithColor("피해 (4)", ConsoleColor.Red); Log("를 받았습니다.", true); this.monsterHp -= this.heroAttackDamage; if (this.monsterHp <= 0) this.monsterHp = 0; Log($"몬스터의 체력은({monsterHp}/{maxMonsterHp})입니다."); if (this.monsterHp <= 0) { Log($"몬스터가 죽었습니다."); } } private void Log(object value, bool isWriteLine = true) { if(isWriteLine) Console.WriteLine(value); else Console.Write(value); } private void WriteLineWithColor(string value, ConsoleColor color) { Console.BackgroundColor = ConsoleColor.Black; Console.ForegroundColor = color; Console.Write(value); Console.ResetColor(); } private void ClearCurrentConsoleLine() { int currentLineCursor = Console.CursorTop; Console.SetCursorPosition(0, Console.CursorTop); Console.Write(new string(' ', Console.WindowWidth)); Console.SetCursorPosition(0, currentLineCursor); } } } | cs |