본문 바로가기

CS

(10)
[CS] SOLID 원칙 SOLID 원칙은 객체지향 설계에서 유지보수성과 확장성을 높이기 위한 다섯 가지 핵심 원칙입니다. 단일 책임 원칙SOLID에서 가장 중요한 첫 번째 원칙, 클래스 또는 함수가 오직 한 가지만 책임집니다.다르게 말하자면 하나의 큰 클래스를 만들기보다는 여러 개의 작은 클래스를 만드는 편이 좋다는 것입니다 . 개방-폐쇄 원칙 클래스가 확장에는 개방적이되 수정에는 폐쇄적이어야 합니다.원본 코드를 수정하지 않고도 새로운 동작을 생성할 수 있도록 클래스를 구조화하세요.어떻게? 인터페이스와 추상화를 이용해서 리스코프 치환 원칙 파생된 클래스가 기본 클래스로 대체될 수 있어야 합니다.파생 클래스에만 있는 기능을 인터페이스 또는 별도 클래스로 옮겨 합성하세요. 인터페이스 분리 원칙어떠한 클라이언트도 자신이 사..
[CS] 컴퓨터 구조와 CPU 메인 메모리 (RAM) 컴파일이 완료된 프로그램 코드가 올라가서 실행되는 영역 프로그램을 다운 받으면 하드디스크에 저장되지만, 실행하면 프로그램이 메인 메모리에 올라간다. 입출력 버스 (I/O Bus) 컴퓨터 구성요소 사이에서 데이터를 주고 받기 위해 사용되는 경로 데이터 종류와 역할에 따라 어드레스 버스, 데이터 버스, 컨트롤 버스로 나뉨 CPU 내부 ALU(Arithmetic Logic Unit) CPU에서 실제 연산을 담당하는 블록 대부분은 산술연산(+-*/...)과 논리 연산(AND, OR)으로 이루어진다. CU(Control Unit) CPU가 처리해야 할 명령어들을 해석 명령어가 CPU 내부로 흘러들어가면 2진수로 구성되어있는 명령어를 ALU가 이해할 수 있게 해석한다. 레지스터 CPU 내부에..
[어셈블리] 스택 메모리 스택은 함수가 사용하는 메모장으로 매개변수 전달과 돌아갈 주소 관리를 한다. 위 이미지처럼 스택은 높은 주소부터 시작해서 쌓여나가며 함수가 실행될 때 마다 지역 변수, 반환 주소값 매개변수가 스택에 쌓인다. 그리고 함수가 종료될 때 스택에서 소멸한다. 레지스터는 다양한 용도로 사용되는데 a b c d 같은 범용 레지스터 말고도 위치를 가리키는 포인터 레지스터가 있다. ip (instruction pointer) : 다음 수행 명령어의 위치 sp (stack pointer) : 현재 스택 top 위치 bp (base pointer) : 스택 상대 주소 계산용 그리고 위 삼총사들을 알아놔야 한다. 함수호출 전에 매개변수들을 push하고 call 함수로 호출하면 함수가 끝나고 다음에 실행해야 할 주소(반환 주..
[어셈블리] 배열 어셈블리에서 배열은 위와 같이 표현할 수 있다. a배열은 1~5까지 배열이고 b의 times는 같은 데이터를 반복할 때 사용한다. b는 초기값이 1인 dword 크기의 요소를 5개 가진 배열이다. 그렇다면 a배열의 각 요소들에 접근을 어떻게 할까? a자체는 배열의 주소를 나타내므로 [a]로 배열 자체를 가져온다. 그렇게 1바이트를 출력하면 맨 앞 1이 출력된다. 그리고 그 이후 배열의 요소도 인접해있으므로 [a+1]로 두번째, [a+2]로 세번째.. 이렇게 요소들을 출력할 수 있다.
[어셈블리] 반복문 위는 Hello World를 10번 반복해서 출력하는 반복문이다. 반복문이지만 사실상 이전 분기문과 다름없다. msg 변수를 출력하면서 ecx를 초기에 10으로 설정하고 (사진에서 짤림) 1씩 ecx를 감소시킨다. 그리고 0과 비교해서 0이 아니라면 다시 LABEL_LOOP를 돌린다. 따로 반복문을 위한 문법도 있다. loop를 사용하면 자동으로 루프마다 ecx를 1씩 줄여나가면서 반복실행한다. 위 코드는 1부터 100까지 합을 구하는 코드이며 xor ebx, ebx는 mov ebx, 0 과 같은 의미이다. (자기자신과 xor하면 0이 나오는 것을 활용)
[어셈블리] 분기문 조건문 CMP dst, src (dst가 기준) destination과 source를 compare 비교를 한 결과물은 Flag Register에 저장 JMP [label] 시리즈 JMP: 무조건 점프 JE: JumpEquals 같으면 점프 JNE: JumpNotEquals 다르면 점프 JG(JumpGreater), JGE(JumpGreaterEquals), JL(JumpLess) 등등... 간단한 예제인데 rax, rbx에 데이터를 저장하고 두 값이 같으면 LABEL_EQUAL로 점프해 rcx를 1을 저장하고 같지 않더라도 무조건 LABEL_EQUAL_END로 점프한다. 왜냐하면 LABEL들도 순차적으로 실행되기 때문에 rax, rbx가 같지 않으면 rcx를 초기값 0으로 그대로 두게 하기 위함이다. ..
[어셈블리] 쉬프트 연산 쉬프트 연산 쉬프트 연산은 비트를 좌측이나 우측으로 옮기는 연산인데, 산술 쉬프트 연산에서는 최상위 비트를 그대로 유지함 ex) 1001 1010 >>1 => 1101 0101 어셈블리에서는 shl, shr을 통해 쉬프트 연산을 할 수 있다. mov eax, 0x12345678 처음에 eax에 4바이트의 데이터를 저장한다. shl eax, 8 =>34567800 shr eax, 8 =>345678 왼쪽으로 8비트(2바이트)만큼 이동했다가 오른쪽으로 다시 8비트만큼 이동했다. 쉬프트 연산을 할 때 1을 하면 마찬가지로 양수일 때 값이 원래 값에 2로 나눈 것과 같다. 그래서 컴파일러가 내부적으로 계산을 할 때 사용하기도 한다.
[어셈블리] 입출력, 사칙 연산 입력 - GET_DEC 데이터크기, 저장할 레지스터(변수) GET_DEC 1,al (레지스터) GET_DEC 1,num (변수) 출력 - PRINT_DEC , GET_DEC와 동일 더하기 - add a,b ( a= a+b ) 메모리끼리 더하는 것은 불가능 add al,[num] => al+[num]의 값이 al에 저장됨 곱하기 - mul bl ( ax= al * bl) 연산결과를 ax에 저장 mul bx ( ax * bx 한 결과를 상위 16비트는 dx에, 하위 16비트는 ax에 저장) 좀 자기 멋대로인듯 나누기 - div bl ( ax / bl) 몫은 al, 나머지는 ah에 저장 얘가 제일 지멋대로다