CreatorB18
1k
2019-05-16 11:59:56 작성 2019-05-16 12:21:39 수정됨
4
94

강제 타입변환 자료형의 출력결과 질문드립니다.


int n = 3 ;

int total = 180;

int max = 80;

double average;


average =  (double) total / max * 10.0 / n ;

System.out.printf("%.2f \n", average);


// 강제 타입변환으로 지정해서 피연산자의 연산이 더블형이 되도록 설정해주었습니다. 이결과는 7.50 이되며 제가 생각한 방식과 일치합니다. 


그러나 다음은 의문점이 생깁니다.


average = 10.0 * total / max / n;

System.out.printf("%.2f \n", average); 


프로그래밍 전용 계산기로 계산해보면 / 10 곱하기 total 나누기 max / 은 22가 나옵니다. 0.5가 드랍되어버립니다.

그럼 결과치는 7.00이 나와야하는데, 실행 결과가 7.50이 나옵니다.


원리가 어떻게되는지 질문드립니다. ㅠ 강사님도 잘 답변해주시지않아서...

0
0
  • 답변 4

  • Frudy
    3k
    2019-05-16 12:20:20 작성 2019-05-16 12:29:26 수정됨

    그럼 결과치는 7.00이 나와야하는데, 컴파일 결과가 7.50이 나옵니다.

    --> 실행결과 라고 정정하시는게 좋을거같아요.


    그리고... 음 질문이 잘 이해 안되서 스스로 해석해보았습니다.


    1.

    프로그래밍 전용 계산기로 계산해보면 10 곱하기 total은 22가 나옵니다.

    -->

    10 * total = 1800입니다만..

    10* total / max = 22가 맞습니다. 이걸 뜻하시는거같구요,


    2.

    10 곱하기 total은 22가 나옵니다. 0.5가 드랍되어버립니다.

    그럼 결과치는 7.00이 나와야하는데, 실행 결과가 7.50이 나옵니다.

    -->

    본문에 기재된 식 = 10.0 * total / max / n;

    말씀하신 식 = 10 * total / max / n;


    말씀하신 식으로 계산하면 당연히 7.00이 나오구요,

    본문에 기재된 식으로 계산하면 7.50가 됩니다. %.2f로 하셨으니까요.


    여기서 햇갈리신거같은대요...


    10.0 * total / max / n; 이 왜 7.5가 되는지는 아실거라 생각하여 생략하려했으나

    시간이 남으므로 적어드릴게요.


    Java는, double * int연산을 할경우 int가 자동으로 double가 됩니다.

    (이걸 자동타입변환 = Promotion이라고 합니다)


    int n = 3;

    double d = 0.5;

    d * (double)n 이렇게 캐스팅하지않아도 된다는 뜻이죠.


    10.0 * total / max / n를 하나씩 뜯어보면 알수있습니다.

    연산 순서는 오른쪽으로 가면 되겠네요?


    1.

    10.0 * (double)total한것 처럼 promotion이 될태니 결과는  1800.0이 됩니다.


    2.

    1800.0 / max 역시 1800.0 / (double)max 한것 처럼 되서 결과는 22.5가 됩니다.


    3.

    22.5 / 3 역시 같은이유로 결과는 7.5가 됩니다.



    반대로, 10 * total / max / n도 해보겠어요.


    1.

    10 * total = 1800  -- int형입니다.


    2.

    1800 / max = 22입니다. 0.5는 버립니다. int / int는 소수점 버리니까요.


    3.

    22 / 3도 위와같은 이유로 7이 됩니다.

    0
  • CreatorB18
    1k
    2019-05-16 12:29:58 작성 2019-05-16 14:01:16 수정됨

    답변 정말 감사합니다. 제가 독학으로 3개월차에 있어서 아직 용어면에서 부족한부분이 많은데 이렇게 짚어주셔서 감사합니다. 

    앞으로는 컴파일결과 라고 하지않고 실행결과라고 정정하겠습니다!! ㅎㅎ 정말감사합니다. 


    그리고 


    말씀하신 2번 부분이 제가 실수로 기입해서 10*total/max로  수정했습니다! 



    먼저 10*total/max를 생각했을때 프로그램 상에서  int형 연산이 되어서 소숫점이 생략이되고 22가나올것같았습니다. 거기서 나누기 n( == 3)을 연산하면  7이 연산이되고 그 int값이 double에 등록이 되어서 7.00이 산출될거라고 예상했습니다. 


    다시말해서 

    average = 10 .0 * total / max / n ; 은 

    double형 average = 10(상수)  | 곱하기 | int형 변수 total | 나누기 | int형 max | 나누기 |  int형 n 


    즉 오른쪽 피연산자가 모두 int형이므로 int형으로 7.0이 계산이될거라 예상했습니다. 



    그런데 실행 결과값은 7.5가 연산이되어서 이상하다고 생각했습니다. ㅠㅠ 



    어디가 틀렸는지 다시한번 여쭤봐도될까요? 



    0
  • CreatorB18
    1k
    2019-05-16 12:33:49 작성 2019-05-16 14:01:50 수정됨

    소스코드 기재합니다.



    package backjoon_input_output;
    
    
    
    import java.util.Scanner;
    
    
    
    public class 평균늘리기 {
    
    
      public static void main(String[] args) {
    
    
        double average;
    
        int total = 0, max = 0;
    
        int score;
    
    
    
        Scanner sc = new Scanner(System.in);
    
    
    
        int n = sc.nextInt();
    
    
    
        for (int i = 0; i < n; i++) {
          score = sc.nextInt();
    
          max = score > max ? score : max;
    
          total += score;
        }
    
    
    
        average =  (double) total / max * 10.0 / n ;
    
        System.out.printf("%.2f \n", average);
    
        average = 10.0 * total / max / n;
    
        System.out.printf("%.2f \n", average); 
    
      }
    
    }
    
    
    // 입력 : 
    // 3, 
    // 40, 60, 80



    0
  • Frudy
    3k
    2019-05-16 13:05:12


    1.

    소스코드가 잘 납득이 안가는대용...

    Scanner로 값을 입력받는 프로그램이면

    어떻게 값을 입력하셨었는지도 알려주세요.


    2.

    다시말해서 

    average = 10 * total / max / n ; 은 

    //

    저 계산식이 소스코드에 없어요.


    average =  (double) total / max * 10.0 / n ;

    average = 10.0 * total / max / n;

    이거 두개밖에 없어요.


    이 계산식 2개로는 말씀하신 n == 3, max = 80, total = 180의 조건에서

    7.50이 나올수밖에 없어요.


    0
  • 로그인을 하시면 답변을 등록할 수 있습니다.