삽질의 현장/- .NET

#063_닷넷(.NET)_.Net Framework 기본 - LINQ 소개 및 관련 기능

shovelman 2015. 11. 6. 16:46


안녕하세요 삽잡이입니다.


이번 시간에는 LINQ가 무엇인지, 그리고 어떤 기능이 들어가있는지에 대해서

간략하게(?) 알아보려고합니다.



LINQ는 Language Intergranted Query를 말합니다.

즉, 통합 쿼리 언어라고 말 할 수 있지요.


LINQ는 데이터 집합 즉, 단일 데이터가 대상이 아닌, 

여러 데이터가 모여있는 집합을 대상으로 사용됩니다.


프로그램의 구조를 살펴보도록 하겠습니다.



쿼리 언어의 대표적인 예로는 SQL이라는 언어가 있습니다.

Structed Query Language로써, APP과 DB를 관리하는 수 많은 DBMS와 소통을 위한 언어입니다.

참고로 DBMS는 DB를 관리하는 어플리케이션 프로그램을 말합니다.


데이터베이스와 이야기하는 표준 언어를 만들었는데

이 데이터베이스와 이야기하고자 하는 표준 언어를 바로 'SQL'이라고 부르는 것입니다.

'Q' 자체가 Query로써 '질의', '물음'을 말하지요.

이 물음에 대한 응답을 해주는 형태의 언어를 바로 SQL이라고 합니다.


대표적인 쿼리 언어로써 DB의 언어입니다. 

표준으로 만들어진 DB의 언어가 SQL이라는 소리입니다.

이 SQL의 장점은 정말 간단하고, 쉽다는 것입니다.

그런데 왜 갑자기 SQL??


쿼리 언어가 한 두개의 적은 데이터를 관리할 때에는 오히려 불편하지만

많은 데이터를 대상으로 관리하고자할 때에는 유용하다는 사실을 알게 되었기 때문에

닷넷에서는 LINQ라는 언어를 통해 제공해주게 되었습니다.


닷넷에서도 많은 데이터 집합을 관리해야할 때가 있을 것입니다.

이 데이터 집합을 좀더 다루기 편하도록 만들었다 이겁니다.

집합 데이터를 다루기 편하도록 만든 쿼리 언어인 'LINQ'. 

지금부터 알아보도록 합시다.


SQL과 다른 LINQ의 핵심은 바로 '강력한 타입 언어'라는 것입니다.

즉, 형식 제약이 엄격한 쿼리 언어라는 것입니다.



타입은 형식입니다.

타입이 강력하다는 것은 형식 제약이 엄격하다는 것입니다.

문자열이라면 오직 문자열, Point 형식이라면 오직 Point형식 처럼

그 외에는 변환을 할 수 없도록 형식 제약이 있다는 것입니다.


LINQ는 강력한 타입의 언어입니다.

쿼리의 특징은 원래 강력하지 않다는 것입니다.

사실, DB에서는 문법 검사를 유연하기 위해 쿼리 언어를 옅게(?) 만들었습니다.

아무튼... 쿼리 언어의 장점을 받아들이면서도, 

프록램을 다룰 때에 필요시 될 수 있는 강력한 형식 제약기능을 추가한 것입니다.

형식 변환에 의해서 데이터를 잘못 관리되는 것을 방지하는 것입니다.


아무튼... LINQ는 강력한 타입의 쿼리 언어임을 기억하시길 바랍니다.


이전시간들에 걸쳐서 배웠지만 

C#에서는 LINQ를 위해서 제공하는 기능들이 몇가지 있습니다.


'익명 메서드', '람다', 'var 타입', 초기화 구문' 등...


이 문법들이 존재하기 때문에 LINQ가 만들어질 수 있는 것이며,

반대로 말하면 해당 문법들은 LINQ를 위한 문법이라는 소리입니다.


이전에 많이들 알아봤었지만...

var타입을 한 번 알아볼까요?


대부분의 LINQ 쿼리는 컴파일 시간까지는 

타입을 정확하게 알 수 없는 일련의 데이터 타입을 반환합니다.

응용 프로그램을 컴파일하기 전까지는 변수의 타입이 무엇인지 알 수 없기 때문에

변수를 명시적으로 선언할 수 없다는 것입니다.

LINQ한테 얻은 결과에 대한 타입을 알아야되는데 뭘 반환할지 모른다는 소리입니다.


그런데, 컴파일할 때에 결정이 됩니다.

타입이 컴파일러에 의해 결정이 되기 때문에 var 타입을 사용하는 것입니다.

Coding Time이라고 하는데... 

우리가 타입을 알 수 없는데 이를 위해 사용하는 타입이 var 타입입니다.



컬렉션을 초기화 할 때 사용하는 문법입니다. 

즉, 초기화 구문을 말하는 것입니다.

두 방법은 모두 똑같이 초기화를 하는 것입니다.


왜 갑자기 초기화 구문을 말했느냐?
바로 '익명 타입'에 대해서 설명하기 위해서입니다.

익명 타입은 타입에 이름이 없다는 것입니다.

타입에 이름이 없다면, 객체를 어떻게 만들어 낼 수 있을까요?


익명 타입은 간단하게 new 즉, 객체의 초기화 문법을 사용합니다.

좀 전에 보여드렸던 초기화 구문은 컬렉션의 초기화 문법이었습니다.



기존 객체의 초기화는 new 연산을 통해 생성자를 호출함으로써 초기화를 했습니다.

객체의 초기화 문법을 사용할 때에 속성을 사용할 수 있기 때문에 가능하지요.


어찌됬건 이 초기화의 문법과 비슷하게

익명 타입은 'var 타입'을 합친 초기화 문법을 통해 만들 수 있게 됩니다.

즉, 익명 타입은 '객체의 초기화 문법' + 'var 타입' 이라는 소리입니다.



타입이 없습니다.

컴파일러가 타입을 만들어주기 때문에 이를 '익명 타입'이라고 부르는 것입니다.


우리가 알 수 있는 정보는 단 하나입니다.

바로, 컴파일러가 만들어 낼 이 타입이 X, Y라는 속성을 가지고 있다는 것입니다.

이 외에는 우리는 모릅니다.

단지, 컴파일러가 X, Y 속성을 받는 이름 없는 타입을 만들어 줄 뿐입니다.

이름은 갖지만, 임의의 이름을 갖도록 타입을 만들어주는 것입니다.


컴파일 시점에서 타입이 명확해지기 때문에 그때서야 var 타입이 결정되게 됩니다.

이것이 바로 익명 타입의 문법입니다.


이런 익명 타입이 어떻게 사용될까요?

예를 들어 쿼리를 던지는데

나이와 이름으로만 이루어진 집합을 가져오라고 하면 어떻게 할겁니까?

이름이면 이름, 나이면 나이! 이렇게 가져온다고 하면

각각 문자열 집합을 만들면 되고, int형 집합을 만들면 되는데...

이름과 나이가 짬뽕된 집합은 어떻게 할 수 있을까요? 그런 타입이 있을까요? 

따라서 해당 집합에 대한 객체를 만들어야될 터인데, 

이 때 익명 타입을 사용하는 것입니다.



따라서 익명 타입이 LINQ에서 필요한 것입니다.

익명 타입이 Age와 Name이라는 속성을 갖고,

Age는 int 타입, Name은 string 타입으로 된 익명 타입이 만들어진 것이지요.


이 외에

람다와 확장 메서드는 이전에 자세하게 알아본 적이 있기 때문에

필요하시다면 해당 글을 읽으시면 좋을 것 같습니다!


이번 시간에는 여기까지 알아보도록 하겠습니다.

이상 삽잡이였습니다!