우선 좀더 자세한 설명을 해줌. 사실 우리가 콘솔창에 ajksdlfjasdklfjl 를 치고 지우지만 엔터를 쳐서 asdfasfjkl 가 이미 입력한후에는
지울수 없는이유가 바로 이 stream 개념 때문에 그럼. OS 에서 하드웨어 인터럽트로 키보드 마우스 입력을 받는다해도 그게 바로 다이렉트로
써지는게아니라 입력버퍼에 차근차근 쌓이게됨. 콘솔창에 10101010만 치게되면 아직 입력버퍼에 들어간게 아니므로 얼마든 수정이가능하다
그말임.문제는 엔터를 친후에는 이게 입력버퍼에 쌓이지
예를들어
scanf("%d",& (type Int));
의입력을하고 니가 3 엔터를 누르면 3이 정상적으로 int형에들어가짐. 하지만 컴퓨터입장에서보면 네가 눌른 엔터도 집어넣어지게 된다 그말이야
즉 3은 int 에들어가지만 오갈데없는 엔터는 입력 버퍼에 남아버리지. 근데 컴파일러는 똑똑해서 이거 scanf를 이용해서 여러개를 입력받는다해도
입력버퍼에 남은 엔터를 자동으로지워주게 돼 문제는 여기서시작됨
gets( char*) 나 getline(cin, string) 따위의 라인을 받게되면 입력버퍼 도 하나의 인풋으로 보게되고 이때는 여러가지방법으로 입력버퍼를
지워줘야됨 아까 링크걸린 곳에서 본 방법이든 뭐든간에말이야
가장단간한건 getchar(); 로 없에줘도되긴함 이게 좋은방법은아닌데 효과는확실해서 백준온라인같은 알고리즘풀때는 나도종종쓰긴함
이해가됬는지?
추천드림
뭐 실제로는 엔터 문자를 입력 안하고 입력을 마치는 방법도 있지만(유닉스/리눅스에서는 [Ctrl+D], 도스/윈도우에서는 [Ctrl+Z하고 엔터]). 아무튼 크게 틀린 내용은 없으므로 추천
EOF 는 내가알기로 사용자가 임의로 콘솔입력 종료를 의미해서 return 값으로 제어하는걸로알고있는데 맞아?
음... 엔터를 치면 자동으로 EOF인 걸로 인식하지만 엔터가 아니고 그냥 라인을 끝내고 싶으면 EOF를 치지. 결론을 말하면 니가 알고 있는 게 맞음.
엔터도 EOF 로받아? EOF 란건 input 함수의 return값으로 알고있는데 문자열을 제외한 인풋의 리턴은 대게 -1이 EOF 0이 형식이나 인풋 지정이 잘못된거 1이 옳은입력인데 엔터자체가 EOF야?
그럼 while(scanf("%d",∫)) 할때 엔터치면 안되지않음?
getchar 같은 함수에서나 EOF가 특수하게 -1로 받아들이지 아스키 코드 표에 보면 EOT(End Of Text) 0x03 이라고 EOF에 대응하는 문자가 존재. 그게 바로 리눅스의 Ctrl+D야.
아. 순간 헷갈렸다. End Of Text가 아니라 End Of Transmission이고 코드는 0x03이 아니라 0x04(Ctrl+A = 0x01, Ctrl+B = 0x02, ...). End Of Text는 ETX(End Of Text) 0x03임.
어 내가잘못알고있나?
http://www.cplusplus.com/reference/cstdio/EOF/
C++ 레퍼런스에서는 EOF 를 -1로 정의하고있더라
EOT 문자가 들어오면 터미널은 그 라인의 입력이 끝난 걸로 간주한다. 만약 아무 글자도 안 입력하고 EOT 문자를 치면 입력이 완전히 끝나게 되고. 그게 바로 EOF(End Of File).
문자열입력함수는 널포인터를반환해서 알아서 0처리해줘서 그게 EOF 지만 레퍼런스에서 -1을 EOF 라고정의하던데
ㅇㅇ. EOF를 -1로 정의한 건 getchar() 함수의 리턴 값 정의에서나 그렇고. ASCII 코드 표에도 EOF(End Of File) 문자가 별도로 존재해.
그럼 실제로 scanf의 return 을 이용해서 ctrl z같은걸로 한게 엄밀히말하면 EOT란말인가요?
아스키 코드 상으로 EOF 문자는 SUB(Subtitute) 문자임.
http://en.wikipedia.org/wiki/Substitute_character.
리눅스에서 줄 입력을 끝낼 때 Ctrl+D를 쓰는데 윈도우에서는 Ctrl+Z를 쓰는 이유가 이 SUB 문자를 지정하기 위함임. Z가 26이고 SUB 문자의 아스키 코드도 26(0x1A)임.
ㅇㅇ 문자가 입력된 상태에서 Ctrl+Z(EOF)를 지정할 경우 EOT 문자처럼 동작함. 스트림을 안 닫고 다음 라인을 또 입력 받지.
왜 하필 SUB 문자냐고 물어보면 뭐... MS-DOS 시절부터 내려온 관습임.
터미널에서 Ctrl+A = 아스키 코드 0x01, Ctrl+B = 아스키 코드 0x02, ... 순으로 Ctrl+A가 아스키 코드 1로, Ctrl+B가 아스키 코드 2로, ... Ctrl+Z가 26으로 매핑됨. 가령 cmd 창에서 Ctrl+G 치고 엔터 누르면 삑 소리 나는 이유가 '\\a' (BEL 문자 = 아스키 코드 0x07)을 입력했기 때문.
야 이런게있었네 신기하네 이게 소스에서 우리가 while(scanf())로 제어하는건 EOT고 이건 걍 각라인당 입력할당 그리고 전체 입력이 종료되는 시점이 EOF란말이네 ㅎㅎ
이게 터미널에서만 쓰이는 개념이 아니라 윈도우 프로그래밍할 때 창 이벤트 받을 때도 해당 되는 듯함. 비주얼 베이직 프로그래밍할 때 텍스트 박스의 KeyPress 이벤트에 KeyAscii라고 값이 들어오는데 이 값을 1~26 인지 비교하면 Ctrl+A~Ctrl+Z 입력을 감지할 수 있음. If KeyPress = 1 Then 해서 Ctrl+A 누르면 텍스트 박스 전체 선택되는 걸 구현하곤 했지.
ㅇㅇ 정확하게 이해했네. EOT(도스/윈도우에서는 SUB)를 입력하면 한 줄의 입력이 끝나는데, 만일 아무 것도 안 입력하고 EOT를 입력하면 그게 바로 EOF가 되는 거지.
그러면 입력 함수에서 내부적으로 알아서 입력 스트림을 닫아 줌.
그럼 실제로 OS상에서 우리가 일반적으로쓰는 ctrl c v ctrl alt del 같은건 위와 다른개념임? c 나 v a 같은 건 ㅅㅅㅅ 말대로 매핑시켜서 작동되게 하는거같고 ctrl alt del 은 걍 시스템 인터럽트같은 그런개념인가?
음... Ctrl+Alt+Del은 리얼 모드(16비트) 도스 환경에서는 키보드에서 키보드 컨트롤러 라인으로 강제 재부팅 신호를 직접 보내주는 것으로 보이고(컴퓨터 구조에서 파워가 키보드 라인이랑 직접 연결되어 있는 걸로 앎), 32비트 보호 모드, 그러니까 지금 쓰는 윈도우나 리눅스 같은 환경에서는 이걸 override시켜서 강제 재부팅이 되게 되는 대신에 운영체제 자체적으로 구현한 기능이 불리게끔 한 것으로 보임. 나도 이 부분은 자세히 살펴보지 않아서 여기까지만 답변을 ㅋㅋㅋ
ㄷㄷ해
아무튼 윈도우에선 Ctrl+Alt+Del 누르면 커널에서 바로 직접적으로 winlogon.exe 속 GINA 라이브러리(msgina.dll)를 호출하는데, 이게 하는 역할이 Windows XP에서는 기본으로 작업 관리자가 뜨지만 Windows Vista 이상에서는 사용자 전환 창이 뜨는데 이게 GINA.
와 그렇다면 대단한놈들이네 ps2 방식키보드야 워낙 핀배치나 그런걸통해서 할수있긴한데 이거 usb로 내려가면 usb 드라이버로 인식해서 ID 값뭐 블라블라해서 디바이스드라이버쪽으로 넘어가는데 USB Ps2 방식 상관없이 만들었단 소리인데 참대단한거같다.. 디바이스에서 인식되는 시스템 자체가 다른데 그신호를 변환해줄수있다니;
음. USB HID 키보드 장치의 경우는 BIOS에서 PS/2처럼 에뮬레이션해 주겠지. 그래서 USB 키보드도 전원 버튼이나 이런 걸 넣을 수 있는 거고.
아항 ㅋㅋㅋㅋ
나도 BIOS 내부에서 USB HID 키보드 장치들을 어떻게 처리하는지 자세히는 모르는데, PS/2나 USB 키보드나 일관되게 동작해야 하기 때문에 PS/2로 돌아가게끔 에뮬레이션했을 거라고 추측만 하고 있음. 아무튼 도움 되었으면 좋겠네 ㅋㅋ