scanf 입력오류 질문입니다.

jong104b의 이미지

//getBMI.c 1. 함수원형 선언
/*****     2. 함수설명
파일이름: getBMI.c
기능    : 10명의 학생 지수를 입력받아 비만도를 출력한다.
작성자  : 변종현
작성일자: 2023.4.28
*****/
 
#include <stdio.h> // printf, scanf 함수원형 복사지시 매크로
 
#define STUDENTS 10
 
// 3. 자료형 설계
typedef unsigned short int UShort;
 
typedef struct _student {
	char name[11];
	float height;
	float weight;
	UShort BMI;
	char (*degree);
} Student;
 
// 4. 함수원형
int main(int argc, char *argv[]);
void Input(Student (*students));
void getBMI(Student (*students), UShort *high, UShort *over, UShort *normal, UShort *low);
void Output(Student (*students), UShort high, UShort over, UShort normal, UShort low);
 
// 5. 함수정의
int main(int argc, char *argv[]){
	Student students[STUDENTS];
	UShort high;
	UShort over;
	UShort normal;
	UShort low;
 
	// 함수호출문장
	Input(students); // 성명들과 점수들을 입력받는다.
	// 신체질량지수를 구하다
	getBMI(students, &high, &over, &normal, &low);
	// 학생들, 신체질량지수, 사람수를 출력하다
	Output(students, high, over, normal, low);
 
	return 0;
}
 
/*****
함수이름 : Input
기 능    : 키보드로 학생들을 입력받는다.
입 력    : 없음
출 력    : 학생들
*****/
 
void Input(Student (*students)){
	UShort i; // 반복제어변수
 
	// STUDENTS번 반복한다.
	for(i=0; i<STUDENTS; i++){
		// 키보드 입력처리
		scanf("%s %.1f %.1f", students[i].name, &students[i].height, &students[i].weight);
	}
}
 
/*****
함수이름 : getBMI
기 능    : 학생들을 입력받아 신체질량지수를 구한다.
입 력    : 학생들
출 력    : 학생들, 비만도
*****/
void getBMI(Student (*students), UShort *high, UShort *over, UShort *normal, UShort *low){
	// 자동변수선언 및 초기화
	UShort i;
	*high = 0;
	*over = 0;
	*normal = 0;
	*low = 0;
 
	// 1. 학생들을 입력받는다.
	// 2. STUDENTS만큼 반복한다
	for(i=0; i<STUDENTS; i++){
		// 2.1 비만도를 구한다.
		students[i].BMI = ((students[i].weight/((students[i].height/100)*(students[i].height/100)))+0.5);
 
		if(students[i].BMI > 30){
			students[i].degree = "High";
			(*high)++;
		}
		else if(students[i].BMI >= 25 && students[i].BMI <= 30){
			students[i].degree = "Over";
			(*over)++;
		}
		else if(students[i].BMI >= 19 && students[i].BMI <=24){
			students[i].degree = "Normal";
			(*normal)++;
		}
		else{
			students[i].degree = "Low";
			(*low)++;
		}
	}
 
	// 3. 비만도를 출력하다.
	// 4. 끝내다
}
 
/*****
함수이름 : Output
기 능    : 학생들을 입력받아 비만도를 출력한다.
입력     : 학생들, 비만도
출력     : 없음
*****/
void Output(Student (*students), UShort high, UShort over, UShort normal, UShort low){
	UShort i;
 
	printf("=====\n");
	printf("번호\t품명\t단가\t수량\t금액\n");
	printf("-----\n");
	for(i=0; i<STUDENTS; i++) { // 학생들 비만도 출력코드
		printf("%3d\t%s\t%.1f\t%.1f\t%hu\t%s\n", i+1, students[i].name, &students[i].height, &students[i].weight, &students[i].BMI, students[i].degree);
	}
	printf("-----\n");
	printf("비만:%3d\t과체중:%3d\t정상:%3d\t저체중:%3d\n", high, over, normal, low);
}

**********
질문입니다. 10명의 정보를 입력받을 수 있게 레코드형 자료를 선언하였습니다.
실제 컴파일 후 입력을 하면 struct 레코드에 자료가 다 입력되지 않습니다. 어디가 문제인지 혹시 물어볼 수 있을까요?

isanghan의 이미지

for문이 좀 특이한데.. 파라메타가 2개로도 돌아가는 건가요..
지금 컴파일 할 여건이 안되서 정확하지 않을 지도 모르겠지만
이 코드면 for문의 i가 0에서 안올라 갈 것 같네요..

--=--=--=--=--=--=--=--=--=--=--=--=--=--=--=--
N년째 초보입니다

지나가다가의 이미지

비교 기호 (<) 가 잘렸을 것 같아요.

jong104b의 이미지

scanf함수에서 값이 제대로 들어가지 않아서 물어봤습니다. 복붙한 코드는 아닙니다. 전산원 조교님하고 상의해보고 수정하고 나면 코드 올려보겠습니다.

세벌의 이미지

kldp에서 소스 코드 올릴 때 주의
소스 코드는 code 블럭으로 감싸야 제대로 보입니다.
안 그러면 제대로 안 올라갑니다. 들여쓰기도 엉망이 됩니다.
그러면 다른 분이 알아보기도 어렵고 그러면, 좋은 답을 얻기 어려워집니다.

jong104b의 이미지

예, 알겠습니다. 수정해보겠습니다.

라스코니의 이미지

scanf() 함수는 위와 같이 정형화된 사용자 입력을 처리하는데 치명적인 단점이 있습니다. 그것은 입력 끝에 사용자가 carriage return (CR) 키를 친 후에 그 문자열이 입력 버퍼에 들어가고 scanf()가 그 입력 버퍼를 읽어서 처리하는데 다 끝나고 난 후 CR 키가 입력 버퍼에 남아서 발생하는 문제점입니다. 단 한번만 호출되면 상관없을 수도 있지만 여러번 호출하는 경우 사용자가 넣은 값이 들어가는 것이 아니라 CR이 들어가는 것이죠.

이것을 해결하는 방법은 여러가지가 있겠지만 추천할 만한 것은 gets()로 사용자 입력을 읽고 sscanf()로 그것을 처리하는 겁니다. 아래처럼요.

char input[64];
int readCnt;
gets(input);
readCnt = sscanf(input, "%s %.1f %.1f", students[i].name, &students[i].height, &students[i].weight);
assert(readCnt == 3);

컴파일 안해봤습니다.

jong104b의 이미지

//getBMI.c 1. 함수원형 선언
/*****     2. 함수설명
파일이름: getBMI.c
기능    : 10명의 학생 지수를 입력받아 비만도를 출력한다.
작성자  : 변종현
작성일자: 2023.4.28
*****/
 
#include <stdio.h> // printf, scanf 함수원형 복사지시 매크로
 
#define STUDENTS 10
 
// 3. 자료형 설계
typedef unsigned short int UShort;
 
typedef struct _student {
	char name[11];
	float height;
	float weight;
	UShort BMI;
	char (*degree);
} Student;
 
// 4. 함수원형
int main(int argc, char *argv[]);
void Input(Student (*students));
void getBMI(Student (*students), UShort *high, UShort *over, UShort *normal, UShort *low);
void Output(Student (*students), UShort high, UShort over, UShort normal, UShort low);
 
// 5. 함수정의
int main(int argc, char *argv[]){
	Student students[STUDENTS];
	UShort high;
	UShort over;
	UShort normal;
	UShort low;
 
	// 함수호출문장
	Input(students); // 성명들과 점수들을 입력받는다.
	// 신체질량지수를 구하다
	getBMI(students, &high, &over, &normal, &low);
	// 학생들, 신체질량지수, 사람수를 출력하다
	Output(students, high, over, normal, low);
 
	return 0;
}
 
/*****
함수이름 : Input
기 능    : 키보드로 학생들을 입력받는다.
입 력    : 없음
출 력    : 학생들
*****/
 
void Input(Student (*students)){
	UShort i; // 반복제어변수
 
	// STUDENTS번 반복한다.
	for(i=0; i<STUDENTS; i++){
		// 키보드 입력처리
		scanf("%s %f %f", students[i].name, &students[i].height, &students[i].weight);
	}
}
 
/*****
함수이름 : getBMI
기 능    : 학생들을 입력받아 신체질량지수를 구한다.
입 력    : 학생들
출 력    : 학생들, 비만도
*****/
void getBMI(Student (*students), UShort *high, UShort *over, UShort *normal, UShort *low){
	// 자동변수선언 및 초기화
	UShort i;
	*high = 0;
	*over = 0;
	*normal = 0;
	*low = 0;
 
	// 1. 학생들을 입력받는다.
	// 2. STUDENTS만큼 반복한다
	for(i=0; i<STUDENTS; i++){
		// 2.1 비만도를 구한다.
		students[i].BMI = ((students[i].weight/((students[i].height/100)*(students[i].height/100)))+0.5);
 
		if(students[i].BMI > 30){
			students[i].degree = "High";
			(*high)++;
		}
		else if(students[i].BMI >= 25 && students[i].BMI <= 30){
			students[i].degree = "Over";
			(*over)++;
		}
		else if(students[i].BMI >= 19 && students[i].BMI <=24){
			students[i].degree = "Normal";
			(*normal)++;
		}
		else{
			students[i].degree = "Low";
			(*low)++;
		}
	}
 
	// 3. 비만도를 출력하다.
	// 4. 끝내다
}
 
/*****
함수이름 : Output
기 능    : 학생들을 입력받아 비만도를 출력한다.
입력     : 학생들, 비만도
출력     : 없음
*****/
void Output(Student (*students), UShort high, UShort over, UShort normal, UShort low){
	UShort i;
 
	printf("=====\n");
	printf("번호\t성명\t키(cm)\t체중(kg)\tBMI\t비만정도\n");
	printf("-----\n");
	for(i=0; i<STUDENTS; i++) { // 학생들 비만도 출력코드
		printf("%3d\t%s\t%.1f\t%.1f\t%3d\t%s\n", i+1, students[i].name, students[i].height, students[i].weight, students[i].BMI, students[i].degree);
	}
	printf("-----\n");
	printf("비만:%3d\t과체중:%3d\t정상:%3d\t저체중:%3d\n", high, over, normal, low);
}

생각보다 간단한 문제였습니다. 지적해주신 부분은 제 역량에서 아직 무슨 이야기인지 조금 어려웠어요.
scanf(%s %f %f)로 수정하니 레코드 각 배열에 입력이 되었습니다. 답변 주셔서 고맙습니다. 나중에 지적해주신 부분은 제 코드분석실력이 나아졌을 때 활용해보겠습니다.

라스코니의 이미지

아마 전체 10개 입력을 한번에 key in 하셨나 보네요. 맞나요?

jong104b의 이미지

더 복잡한 내용은 아직 제가 소화를 못 해서 이렇게 말씀드립니다.

jong104b의 이미지

//getBMI.c 1. 함수원형 선언
/*****     2. 함수설명
파일이름: getBMI.c
기능    : 10명의 학생 지수를 입력받아 비만도를 출력한다.
작성자  : 변종현
작성일자: 2023.4.28
*****/
 
#include <stdio.h> // printf, scanf 함수원형 복사지시 매크로
 
#define STUDENTS 10
 
// 3. 자료형 설계
typedef unsigned short int UShort;
 
typedef struct _student {
	char name[11];
	float height;
	float weight;
	UShort BMI;
	char (*degree);
} Student;
 
// 4. 함수원형
int main(int argc, char *argv[]);
void Input(Student (*students));
void getBMI(Student (*students), UShort *high, UShort *over, UShort *normal, UShort *low);
void Output(Student (*students), UShort high, UShort over, UShort normal, UShort low);
 
// 5. 함수정의
int main(int argc, char *argv[]){
	Student students[STUDENTS];
	UShort high;
	UShort over;
	UShort normal;
	UShort low;
 
	// 함수호출문장
	Input(students); // 성명들과 점수들을 입력받는다.
	// 신체질량지수를 구하다
	getBMI(students, &high, &over, &normal, &low);
	// 학생들, 신체질량지수, 사람수를 출력하다
	Output(students, high, over, normal, low);
 
	return 0;
}
 
/*****
함수이름 : Input
기 능    : 키보드로 학생들을 입력받는다.
입 력    : 없음
출 력    : 학생들
*****/
 
void Input(Student (*students)){
	UShort i; // 반복제어변수
 
	// STUDENTS번 반복한다.
	for(i=0; i<STUDENTS; i++){
		// 키보드 입력처리
		scanf("%s %f %f", students[i].name, &students[i].height, &students[i].weight);
	}
}
 
/*****
함수이름 : getBMI
기 능    : 학생들을 입력받아 신체질량지수를 구한다.
입 력    : 학생들
출 력    : 학생들, 비만도
*****/
void getBMI(Student (*students), UShort *high, UShort *over, UShort *normal, UShort *low){
	// 자동변수선언 및 초기화
	UShort i;
	*high = 0;
	*over = 0;
	*normal = 0;
	*low = 0;
 
	// 1. 학생들을 입력받는다.
	// 2. STUDENTS만큼 반복한다
	for(i=0; i<STUDENTS; i++){
		// 2.1 비만도를 구한다.
		students[i].BMI = ((students[i].weight/((students[i].height/100)*(students[i].height/100)))+0.5);
 
		if(students[i].BMI > 30){
			students[i].degree = "High";
			(*high)++;
		}
		else if(students[i].BMI >= 25 && students[i].BMI <= 30){
			students[i].degree = "Over";
			(*over)++;
		}
		else if(students[i].BMI >= 19 && students[i].BMI <=24){
			students[i].degree = "Normal";
			(*normal)++;
		}
		else{
			students[i].degree = "Low";
			(*low)++;
		}
	}
 
	// 3. 비만도를 출력하다.
	// 4. 끝내다
}
 
/*****
함수이름 : Output
기 능    : 학생들을 입력받아 비만도를 출력한다.
입력     : 학생들, 비만도
출력     : 없음
*****/
void Output(Student (*students), UShort high, UShort over, UShort normal, UShort low){
	UShort i;
 
	printf("=====\n");
	printf("번호\t성명\t키(cm)\t체중(kg)\tBMI\t비만정도\n");
	printf("-----\n");
	for(i=0; i<STUDENTS; i++) { // 학생들 비만도 출력코드
		printf("%3d\t%s\t%.1f\t%.1f\t%3d\t%s\n", i+1, students[i].name, students[i].height, students[i].weight, students[i].BMI, students[i].degree);
	}
	printf("-----\n");
	printf("비만:%3d\t과체중:%3d\t정상:%3d\t저체중:%3d\n", high, over, normal, low);
}

생각보다 간단한 문제였습니다. 지적해주신 부분은 제 역량에서 아직 무슨 이야기인지 조금 어려웠어요.
scanf(%s %f %f)로 수정하니 레코드 각 배열에 입력이 되었습니다. 추가로 출력에서도 &연산자를 삭제해야 제대로 출력이 되었습니다. 답변 주셔서 고맙습니다. 나중에 지적해주신 부분은 제 코드분석실력이 나아졌을 때 활용해보겠습니다.

댓글 달기

Filtered HTML

  • 텍스트에 BBCode 태그를 사용할 수 있습니다. URL은 자동으로 링크 됩니다.
  • 사용할 수 있는 HTML 태그: <p><div><span><br><a><em><strong><del><ins><b><i><u><s><pre><code><cite><blockquote><ul><ol><li><dl><dt><dd><table><tr><td><th><thead><tbody><h1><h2><h3><h4><h5><h6><img><embed><object><param><hr>
  • 다음 태그를 이용하여 소스 코드 구문 강조를 할 수 있습니다: <code>, <blockcode>, <apache>, <applescript>, <autoconf>, <awk>, <bash>, <c>, <cpp>, <css>, <diff>, <drupal5>, <drupal6>, <gdb>, <html>, <html5>, <java>, <javascript>, <ldif>, <lua>, <make>, <mysql>, <perl>, <perl6>, <php>, <pgsql>, <proftpd>, <python>, <reg>, <spec>, <ruby>. 지원하는 태그 형식: <foo>, [foo].
  • web 주소와/이메일 주소를 클릭할 수 있는 링크로 자동으로 바꿉니다.

BBCode

  • 텍스트에 BBCode 태그를 사용할 수 있습니다. URL은 자동으로 링크 됩니다.
  • 다음 태그를 이용하여 소스 코드 구문 강조를 할 수 있습니다: <code>, <blockcode>, <apache>, <applescript>, <autoconf>, <awk>, <bash>, <c>, <cpp>, <css>, <diff>, <drupal5>, <drupal6>, <gdb>, <html>, <html5>, <java>, <javascript>, <ldif>, <lua>, <make>, <mysql>, <perl>, <perl6>, <php>, <pgsql>, <proftpd>, <python>, <reg>, <spec>, <ruby>. 지원하는 태그 형식: <foo>, [foo].
  • 사용할 수 있는 HTML 태그: <p><div><span><br><a><em><strong><del><ins><b><i><u><s><pre><code><cite><blockquote><ul><ol><li><dl><dt><dd><table><tr><td><th><thead><tbody><h1><h2><h3><h4><h5><h6><img><embed><object><param>
  • web 주소와/이메일 주소를 클릭할 수 있는 링크로 자동으로 바꿉니다.

Textile

  • 다음 태그를 이용하여 소스 코드 구문 강조를 할 수 있습니다: <code>, <blockcode>, <apache>, <applescript>, <autoconf>, <awk>, <bash>, <c>, <cpp>, <css>, <diff>, <drupal5>, <drupal6>, <gdb>, <html>, <html5>, <java>, <javascript>, <ldif>, <lua>, <make>, <mysql>, <perl>, <perl6>, <php>, <pgsql>, <proftpd>, <python>, <reg>, <spec>, <ruby>. 지원하는 태그 형식: <foo>, [foo].
  • You can use Textile markup to format text.
  • 사용할 수 있는 HTML 태그: <p><div><span><br><a><em><strong><del><ins><b><i><u><s><pre><code><cite><blockquote><ul><ol><li><dl><dt><dd><table><tr><td><th><thead><tbody><h1><h2><h3><h4><h5><h6><img><embed><object><param><hr>

Markdown

  • 다음 태그를 이용하여 소스 코드 구문 강조를 할 수 있습니다: <code>, <blockcode>, <apache>, <applescript>, <autoconf>, <awk>, <bash>, <c>, <cpp>, <css>, <diff>, <drupal5>, <drupal6>, <gdb>, <html>, <html5>, <java>, <javascript>, <ldif>, <lua>, <make>, <mysql>, <perl>, <perl6>, <php>, <pgsql>, <proftpd>, <python>, <reg>, <spec>, <ruby>. 지원하는 태그 형식: <foo>, [foo].
  • Quick Tips:
    • Two or more spaces at a line's end = Line break
    • Double returns = Paragraph
    • *Single asterisks* or _single underscores_ = Emphasis
    • **Double** or __double__ = Strong
    • This is [a link](http://the.link.example.com "The optional title text")
    For complete details on the Markdown syntax, see the Markdown documentation and Markdown Extra documentation for tables, footnotes, and more.
  • web 주소와/이메일 주소를 클릭할 수 있는 링크로 자동으로 바꿉니다.
  • 사용할 수 있는 HTML 태그: <p><div><span><br><a><em><strong><del><ins><b><i><u><s><pre><code><cite><blockquote><ul><ol><li><dl><dt><dd><table><tr><td><th><thead><tbody><h1><h2><h3><h4><h5><h6><img><embed><object><param><hr>

Plain text

  • HTML 태그를 사용할 수 없습니다.
  • web 주소와/이메일 주소를 클릭할 수 있는 링크로 자동으로 바꿉니다.
  • 줄과 단락은 자동으로 분리됩니다.
댓글 첨부 파일
이 댓글에 이미지나 파일을 업로드 합니다.
파일 크기는 8 MB보다 작아야 합니다.
허용할 파일 형식: txt pdf doc xls gif jpg jpeg mp3 png rar zip.
CAPTCHA
이것은 자동으로 스팸을 올리는 것을 막기 위해서 제공됩니다.