배열의 평균값 lv0-> 성공
https://school.programmers.co.kr/learn/courses/30/lessons/120817
프로그래머스
SW개발자를 위한 평가, 교육, 채용까지 Total Solution을 제공하는 개발자 성장을 위한 베이스캠프
programmers.co.kr
/*
나눠 생각하기
매개변수로 주어지는 형태는 이미 숫자 배열 뽑아내기
정수형이므로 double로 어떻게 만들지 고민
제약 파악
항시 .5 .0의 결과만 나온다고 했으니 소수점 표현 고민 ㄴㄴ가 아니라 오차율때문에..
.0인 경우는 그냥 나누어 떨어진다는 의미니까 고민할게 없다.
.5인 경우는 나누어 떨어지지 않는 다는 의미니까 .5로 변환
의사 코드(오류 버전)
1. double 결과를 위해 sum을 double로 0.0 할당
2. 반복문 동안 계속 누적합
3. 마지막에 길이 만큼 나누면 double 결과
4.
의사 코드(개선 버전)
1. 누적합을 위한 int 변수
2. 반복문을 통해 int 누적합
3. 길이 만큼 나누었을때 나머지가 0이 아니라면 +0.5
*/
class Solution {
public double solution(int[] numbers) {
double answer = 0;
// 1. 누적합을 위한 int 변수
int sum = 0;
// 2. 반복문을 통해 int 누적합
for(int i : numbers) sum+=i;
// 3. 길이 만큼 나누었을때 나머지가 0이 아니라면 +0.5
int tempRes = sum/numbers.length;
int tempRest = sum%numbers.length;
if(tempRest!=0) answer = tempRes + 0.5;
else answer = tempRes + 0.0;
return answer;
}
}
[다른 사람 풀이]
import java.util.Arrays;
class Solution {
public double solution(int[] numbers) {
return Arrays.stream(numbers).average().orElse(0);
}
}
[나의 의문]
왜?? 부동소수점 에러에대한 부분을 다들 신경 안쓰는거지??
-> GPT의 답변
https://chatgpt.com/share/67627a6c-d618-800d-a005-4699b9ce04b5
ChatGPT - Average Calculation Precision
Shared via ChatGPT
chatgpt.com
-> 결론 : 실제 부동소수점 표현에서는 실제 바이너리값과 근사값이라는게 존재한다. 더 나아가 종결값과 비종결값이 있음.
종결값과 종결값의 연산 결과 종결값이 나온다면 근사값끼리의 계산으로 처리하지 바이너리값을 고려하지 않는다.
하지만 비종결값이 끼어있으면 근사값 자체가 모호해져서 내가 생각하는 부동소수점의 오차 계산 결과가 나온다.
public class FloatingPointDemo {
public static void main(String[] args) {
// Simple addition: No visible error
double sum1 = 0.1 + 0.3;
System.out.println("0.1 + 0.3 = " + sum1); // Outputs: 0.4
// Adding a non-terminating fraction
double sum2 = (1.0 / 3.0) + 0.1;
System.out.println("(1/3.0) + 0.1 = " + sum2); // Outputs: 0.43333333333333335
// Compare results
System.out.println("Is 0.1 + 0.3 == 0.4? " + (sum1 == 0.4)); // true
System.out.println("Is (1/3.0) + 0.1 == 0.433? " + (sum2 == 0.433)); // false
}
}
배열 뒤집기 lv0 -> 성공
https://school.programmers.co.kr/learn/courses/30/lessons/120821
프로그래머스
SW개발자를 위한 평가, 교육, 채용까지 Total Solution을 제공하는 개발자 성장을 위한 베이스캠프
programmers.co.kr
// [나눠생각하기]
// 원소 순서를 거꾸로 뒤집기위해 같은 배열을 추가한다.
// 뭐 스트림 쓰는 경우도 있을거 같은데 여기선 안쓴다.
// [제약생각하기]
// 길이는 총 1000이다. 뒤집는건 n회면 끝
// [의사코드] -> 오류 발생 형변환
// 1. arrayList를 사용할것 append 코드
//[의사코드] -> 개선
//1. 매서드 내부에 있는 int배열은 호출시점에 크기 결정된다.
class Solution {
public int[] solution(int[] num_list) {
//1. 매서드 내부에 있는 int배열은 호출시점에 크기 결정된다.
int[] answer = new int[num_list.length];
for(int i=num_list.length-1,j=0 ; i>=0; i--, j++){
answer[j] = num_list[i];
}
return answer;
}
}
n^2 배열 자르기 lv2 -> 실패..
https://school.programmers.co.kr/learn/courses/30/lessons/87390
프로그래머스
SW개발자를 위한 평가, 교육, 채용까지 Total Solution을 제공하는 개발자 성장을 위한 베이스캠프
programmers.co.kr
[실패코드]
// [나눠서 생각하기]
// 먼저 주어진대로 만들 수 밖에없다 -> 점화식이나 일반식이 떠오르질 않는다..
// 2차원배열을 나눠서 붙인다.
// left right 대로 자르면 된다.
// [제약 생각]
//그런데 입력값이 생각보다 많으 크다... 10000000 천만이다.. 이거 구현문제가 아니네...
//무조건 1,2,3...n,2,2,3...n,3,3,3...n 이거 규칙이 없진 않네.
// 규칙대로라면 항상 n을 기준으로 특별한 일차원 배열이 생성된다.
// right-left가 일차원 배열의 길이네
// left/n 이 몇번째 패턴인지를 결정하네
// left%n 이 시작 지점을 예측해주고 n-시작지점만큼은 일단 반복하고 총길이에서 계속 이거 반복인데 이거 ...
// [의사코드]
// 1.일단 매개변수를 기준으로 구해야될거 같은거 구해놓는다.
// 2.패턴을 생성하는 매서드를 만들어야 될거 같다.
//패턴은 시작인덱스, 몇번째, 끝인덱스로 받아서 만들어주는거 하나만 있으면
//시작패턴, 중간패턴,...,끝패턴 을 조합하여 일차원 배열을 반환할 수 있을거 같다.
// 3.패턴을 생성하는 매서드가 만들어 졌다면 그걸 총 호출하는 경우의 수를 생각해서 나눠보면
// length가 0이될때까지네.. 이거 계속 length 빼면서 해야되네
class Solution {
public int[] solution(int n, long left, long right) {
// 1.일단 매개변수를 기준으로 구해야될거 같은거 구해놓는다.
int length = right-left+1; //5-2+1=4
int orderfirst = left/n; //2/3=0
int firstidx = left%n; //2%3=2
int
// 3.패턴을 생성하는 매서드가 만들어 졌다면 그걸 총 호출하는 경우의 수를 생각해서 나눠보면
// length가 0이될때까지네.. 이거 계속 length 빼면서 해야되네
while(lenth<=0){
firstidx = 0;
}
int[] answer = {};
return answer;
}
// 2.패턴을 생성하는 매서드를 만들어야 될거 같다.
//패턴은 시작인덱스, 몇번째, 끝인덱스로 받아서 만들어주는거 하나만 있으면
//시작패턴, 중간패턴,...,끝패턴 을 조합하여 일차원 배열을 반환할 수 있을거 같다.
public int[] makePattern(int order, int first, int last, int n){
//담기위한 배열
int[] res = new int[last-first+1];
int cnt = 0;
//시작부터 끝까지 이러면 원하는 길이의 배열 생성
for(int i=first; i<=last ; i++ ){
//first는 개념상 0부터 시작 따라서 항시 +1
//그런데 order에 따라서 first의 변수값이 달라질수 있다. Order가 0이라면 0인덱스까지 상관없어 1부터 시작해
//만약 order가 1이라면 22고
//만약 order가 2라면 333이야
if(i >= order){
res[cnt] = i+1;
}
else if(i<order){
res[cnt] = order+1;
}
cnt++;
}
}
}
진행 요약:
패턴을 생성하는 매서드를 만들고서 거기에 매개변수를 줘야되는데 lastindex값을 어떻게 줘야될지 감이 안잡히고 오래 붙잡아 포기
[다른 사람 해설]
[프로그래머스] n^2 배열 자르기
프로그래머스에서 문제를 풀고 나름대로 정리해본 것 입니다 !
velog.io
내가 하는 방식의 식을 정확히 구현한 사람이 있다면 코드를 찾고 싶지만 아쉽게도 너무 어려운 접근인가보다 안나온다.
다수의 고수들이 사용한 방식은 결국
1. 규칙성 찾기
2. N^2 배열은 필요가 없음
1. 규칙성
- 인덱스/n 은 몇번째 행인지를 표현
- 인덱스%n은 몇번째 열인지를 표현
- 행과 열만 알면 그 중 가장 큰값이 해당 위치의 값이란걸 알기 -> 내가 요걸 생각 못했다.
3번 규칙성을 설명하자면 0번째행은 1234~ 1번째행은 2234~ 2번째행은 3334~ 이다.
자 0,0은 0+1이다. 0,1은 1+1이다. 1,0은 1+1이다 1,1도 1+1이다. 2,0은 2+1이다 2,3이되어야 비로소 3+1이다.
이 규칙성을 무조건 만족하므로 행과 열을 만드는 몫과 나머지로 행열 정보를 알수 있고,
행과 열중 큰값 +1하면 배열의 요소를 만들 수 있다는게 결론
2. n^2 배열은 필요가 없다.
[다른 사람 코드]
굳이 쓰지 않겠다. 이 책 2회독때 다시 돌아와
나누어 떨어지는 숫자 배열 lv1 -> 성공
https://school.programmers.co.kr/learn/courses/30/lessons/12910
프로그래머스
SW개발자를 위한 평가, 교육, 채용까지 Total Solution을 제공하는 개발자 성장을 위한 베이스캠프
programmers.co.kr
[풀이코드]
//나누어 생각하기
// 1. 배열을 탐색하는건 기본. divisor로 나누어 떨어지는경우만 처리하는것도 기본
// 2. 정렬을 어떻게 할까? 잘못하면 굉장히 크기가 커질 수도 있다.
// 2-1. 내 생각에 n이 들어오면 일단 n만큼 탐색횟수가 돌아가고
// 2-2. 최대 n만큼 추가한다면 quicksort nlogn이 돌아갈것
//제약 사항으로 생각하기
// 1. 최대 n의 길이가 주어지지 않았다.. 고려할 정도가 아닐지도 모르겠다.
//의사코드
//1. n번 반복하는 동안 나누어 떨어지는 경우에 temp에 저장
//1-1. 만약 아무것도 없다면 -1 추가
//2. temp를 정렬하는 코드
//3. 정렬된 temp에서 intarray를 추출하여 반환
import java.util.*;
class Solution {
public int[] solution(int[] arr, int divisor) {
int[] answer = {};
//1. n번 반복하는 동안 나누어 떨어지는 경우에 temp에 저장
ArrayList<Integer> ilist = new ArrayList<>();
for(int i : arr){
if(i%divisor == 0) ilist.add(i);
}
//1-1. 만약 아무것도 없다면 -1 추가
if(ilist.size() == 0) ilist.add(-1);
//2. temp를 정렬하는 코드
else Collections.sort(ilist);
//3. 정렬된 temp에서 intarray를 추출하여 반환
return ilist.stream().mapToInt(Integer::intValue).toArray();
}
}
[다른 사람 코드]
일단 Array의 스트림상태에서 필터로 거르고 정렬하면 되는 방법도 있는데 아직 스트림에 익숙하지 않은거 같다.
import java.util.Arrays;
class Solution {
public int[] solution(int[] arr, int divisor) {
int[] answer = Arrays.stream(arr).filter(factor -> factor % divisor == 0).toArray();
if(answer.length == 0) answer = new int[] {-1};
java.util.Arrays.sort(answer);
return answer;
}
}
'Learn > 코딩 테스트 합격자 되기: 자바 편' 카테고리의 다른 글
배열: 실패율 | 방문 길이 (0) | 2024.12.02 |
---|---|
자바로 코딩테스트 준비 (2) : 원시타입-참조타입 / 컬렉션 / 기괴한 매서드 (0) | 2024.12.02 |
배열: 두 개 뽑아서 더하기 / 모의고사 / 행렬의 곱셈 (1) | 2024.12.01 |
자바로 코딩테스트 준비 (1) : 학습법, 효율적인 준비법, 알고리즘 효율 분석 (0) | 2024.12.01 |