오늘 배운 것
01. while
+) prefix, postfix
01. while
○ 반복문 개요
주어진 조건이 참일 때, 해당하는 실행부를 반복 수행하다가 조건식이 거짓이 되는 순간 중단한다.
while, do~while, for 문 등이 있으며 반복의 제어를 위해 break, continue 등을 주로 사용한다.
○ while
조건식이 참일 때, 특정 영역을 반복 수행한다. 반복 횟수가 많거나 정해져 있지 않을 때 주로 사용.
조건이 맞지 않으면 단 한 번도 실행되지 않을 수 있다.
○ while문의 형식 및 구조
while (조건식)
{
// 실행문;
}
실습044
증감연산자 : prefix, postfix (전위/후위 표기법) 또는 구문 위치에 따라 증가 시점을 조절할 수 있다.
// 출력 후 n을 1 증가
int n = 0;
while (n <= 10)
{
System.out.println("n = " + n);
n++ ;
}
// n을 1 증가 후 출력
int n = 0;
while (n <= 10)
{
n++ ;
System.out.println("n = " + n);
}
증가 연산자를 동일하게 postfix로 작성한 예시.
작성 위치에 따라, 연산 대상 변수(n)와 관련된 동일한 구문을 다른 결과로 반환할 수 있다.
int a = 0;
while (a++ <= 10) // 조건식 안에서 수행
{
System.out.println("a = " + ++a);
}
// a => 2 ,4 ,6 ,8, 10 , 12
증감 연산자는 조건식 안에서도 동일하게 동작한다.
첫 루프의 조건식에서 a가 1 증가하고, 출력문에서 한 번 더 1 증가했기 때문에 2부터 출력된다.
실습045
1부터 100까지 정수에서 짝수의 합만 출력
단, 조건문은 사용하지 않고 while 반복문만 활용한다.
- 초기값: 2 , 증가값: 2, 한계값 100
단순히 정상 동작, 값 출력만 생각하고 작성했던 코드.
주어진 조건을 더 꼼꼼하게 살피고, 효율적으로 작성해야겠다.
/* --------- ① 내 풀이 -----------*/
int n = 0;
int sum = 0;
while (n < 100)
{
n++;
n++;
sum += n;
}
/*------- ② 강사님 풀이 ------*/
int n1 = 2;
int sum1 = 0;
while ( n1 <= 100)
{
sum1 += n1;
n1 += 2; // n1을 2씩 증가
}
단순하게 n++를 2번 작성한 점이 눈에 띈다. 만약 7의 배수만 누적합이었다면..(ㅎㅎㅎ)
생활코딩 이고잉님 말씀이 생각난다.. 항상 최악의 경우를 생각하라고.
이 구문을 수백..아니 수억번 반복해야 한다고 생각해봅시다~~(목소리가 들린다 들려..)
실습046
1~100 범위 정수의 짝수 누적합, 홀수 누적합을 따로 계산하고 출력.
while 반복문과 if 조건문을 활용한다.
//상략
int n = 1;
int even = 0; //짝수 누적합
int odd = 0; //홀수 누적합
while (n <= 100)// 100번 반복
{
if (n % 2 == 0) // 짝수일 때
even += n;
else if (n % 2 != 0)// 홀수일 때
odd += n;
else
System.out.println("오류!");// 예외처리
n ++; // n을 1 증가
}
System.out.println("1부터 100까지 정수 중");
System.out.printf("짝수의 합: %d\n홀수의 합: %d\n",even ,odd);
//출력 결과
1부터 100까지 정수 중
짝수의 합: 2550
홀수의 합: 2500
계속하려면 아무 키나 누르십시오 . . . // 하략
실습047
1~100 누적합, 짝수 누적합, 홀수 누적합 출력.
public class Test047{
public static void main(String[] args){
int n = 1;
int sum = 0, even = 0 ,odd = 0;
//cf.) sum = even = odd = 0;
//--> 오른쪽부터 대입. 0을 odd에 → 그 값을 even에 → 그 값을 sum에.
while (n <= 100){
sum += n;
if (n % 2 == 0){
even += n;
}else if(n % 2 != 0){
odd += n;
}else{
System.out.println("오류!");
return; // 메소드를 종료한다.
}
n++ ;
}
System.out.println("1 부터 100 까지 정수의 합" + sum);
System.out.println("1 부터 100 까지 짝수의 합" + even);
System.out.println("1 부터 100 까지 홀수의 합" + odd);
}
}
/*------------------------------------------
1 부터 100 까지 정수의 합5050
1 부터 100 까지 짝수의 합2550
1 부터 100 까지 홀수의 합2500
계속하려면 아무 키나 누르십시오 . . .
-------------------------------------------*/
실습048
1부터 100까지 누적합을 구하고 10의 배수 단위로 반복 출력.
int n = 1, sum = 0;// 루프 변수, 누적합 변수
while (n <= 100)
{
sum += n;
if (n % 10 == 0)
System.out.printf("1부터 %d 까지의 합: %d\n" , n , sum);
n ++;
}//상하략
실습049
1/2 + 2/3 + 3/4 .... + 9/10 의 연산 결과 출력
2/7에 작성한 단순한 코드
int n = 0;
double a = 1, b = 2;
double sum = 0;
while (n < 9) // 9번 반복
{
sum += a / b;
a++;
b++;
n++;
}
2/25. 백지 복습. 다시 작성한 코드
int n2 = 1; // 루프 변수
double sum2 = 0; // 누적합 변수
while(n2 < 10) // 1~9 루프
{
sum2 += (double)n2/(n2 + 1);
n2++;
}
차이점 : 루프 변수를 1로 만들어서 연산에도 활용했다.
변수 2개로 모든 연산을 처리하고, 누적합 변수에 담기 전 명시적 형변환 했다.
실습050
1*2*3*...*9*10 의 누적곱 출력
public class Test050{
public static void main(String[] args){
int n = 1; // 루프 변수
int result = 1; // 1부터 누적곱 시작
while (n < 10 ) // 9번 반복
{
result *= n + 1;
n++;
}
System.out.printf("연산 결과: %d\n", result); // 연산 결과: 3628800
}
}
실습051
임의의 정수를 입력받고, 소수인지 아닌 지 판별, 출력
//상략
int n = 2; //루프 변수를 2로 초기화
boolean isNot = (num % n) == 0 && num != n ;
// 나눠지지만 나누는 값과 입력값이 서로 다르면 소수 아님
if (num == 1){ // 1을 먼저 제외
System.out.println("소수 아님");
}
else{
while (n <= num)//나누는 수가 입력값보다 작거나 같은 동안 반복
{
if (num == n)// 최대값(입력값)까지 도달해야하므로 if로 우선 조건.
{ System.out.println("소수!");
break;
}else if(isNot){// 소수 아님
System.out.println("소수 아님!");
break;
}else{
n++;// 나누는 수 (== 루프 변수)증가
}
}
}//하략
1을 먼저 제외하고 루프변수를 2로 초기화.
if문에서 1을 먼저 제외했으므로 2이상의 수가 while문 안에서 처리된다.
else if 구문에서 불리언 값으로 자기 자신으로 나누어지는지 판별하고
소수가 아니면 break; 아직 판별불가라면 else구문으로 나누는 수를 증가한다.
일단 수를 받아서 판별하고.. true/false로 나눠지지 않으면 수를 증가하면서 다시 판별하는 방식.
문제 내용에서 '설계 포인트: 입력값이 소수가 아니다 VS 소수다 라고 가정 '
이라는 부분이 있었는데 잘 지키지 않아서 복잡하게 작성된 것 같다.
실습051_1(강사님 코드)
public class Test051_1{
public static void main(String[] args) throws IOException{
/*강사님 풀이 :소수가 아닐 때 바로 루프 종료*/
BufferedReader br = new BufferedReader(new InputStreamReader(System.in));
System.out.print("임의의 정수 입력: ");
int num =Integer.parseInt(br.readLine()); // 입력값
int n = 2; // 루프 변수
boolean flag = true; // 맞다고 가정
while (n < num) // 값이 같아지면 루프 종료
{
if (num % n == 0){
flag = false;
break;
}
n++; // 나누어 떨어지지 않으면 n 증가
}
if(flag && num != 1) // 1이 아니면 소수!
System.out.println("소수!");
else
System.out.println("소수 아님!");
}
}
flag 변수를 처음 들어봐서 검색도 따로 해보면서 체크했다.
+) 번외 : outer loop, break label
사용 권장 x. 종종 쓰이긴 함. 가볍게 알아두기
break 문은 자기 자신이 속한 반복문 하나만 벗어난다.
둘 이상의 반복문을 벗어날 때는 브레이크 레이블(break label) 문을 사용한다.
오늘 느낀 점
효율적인 설계를 위한 힌트나 조건이 주어졌을 때 더 깊게 생각해보고 작성해야겠다.
중간에 출력문으로 체크하는 것도 그렇고, 빨리 해결하고 싶다고 급하게 완성하려 할 때가 있다..
'정리 노트 > 쌍용 KDT_(자바 Spring)' 카테고리의 다른 글
23.02.09(목): 반복문 (별 찍기,break, continue), return, 메소드의 재귀 호출 (0) | 2023.03.26 |
---|---|
23.02.08(수): 반복문 (while, do-while, for) + 다중 for문 (0) | 2023.02.27 |
23.02.06(월): 조건문 if, switch (다중 선택문) (0) | 2023.02.23 |
23.02.03(금): 조건 연산자, 윤년/평년, 조건문 if (4) | 2023.02.16 |
23.02.02(목): 기본 입출력, 연산자(비트,논리,삼항...), 특수 문자 영문 이름 (2) | 2023.02.13 |