김영한의 실전 데이터베이스 입문 - 모든 IT인을 위한 SQL 첫걸음(SQL부터 차근차근)
[질문 템플릿] 1. 강의 내용과 관련된 질문인가요? (예/아니오) 2. 인프런의 질문 게시판과 자주 하는 질문에 없는 내용인가요? (예/아니오) 3. 질문 잘하기 메뉴얼을 읽어보셨나요? (예/아니오) [질문 내용] SQL 치다가 갑자기 오류가 나서 확인해보니 my_shop 데이터베이스가 사라지고 아래처럼 RECOVER_YOUR_DATA 무슨 복구프로그램 같은 느낌으로 되어있는데 이건 어떻게 해야하는거죠?
안녕하세요! 최근에 강의를 듣는중 궁금정이 있어 질문을 드리게되었습니다. 다름이 아니라 ReviewPolicyValidator가 있는데, ReviewManager의 update내부에서 // 기존 리뷰 이미지 불러오기 val existingImages = reviewImageRepository.findByReviewIdAndStatus(reviewId, EntityStatus.ACTIVE) // 지정된 이미지 삭제 if (imageHandle.hasImagesToDelete()) { existingImages.filter { it.id in imageHandle.deleteImageIds } .forEach { it.delete() } } // 기존에 이미지가 있었는데 삭제 후 남은 이미지도 없고 새로운 이미지도 없으면 에러 if (existingImages.size > 0 && existingImages.count { it.isActive() } <= 0 && imageHandle.hasImagesToAdd() == false) { throw CoreException(ErrorType.REVIEW_CANNOT_DELETE_ALL_IMAGES) } 요런식의 예외처리가 있더라고요, 제가 생각하기에는 이것또한 하나의 정책의 범주에 들어간다고 생각되는데, 해당 부분이 PolicyValidator가 아닌 Manager에 남게된 이유가 무엇일까요? 개인적인 생각으로는 delete처리가 들어가기전에 filtering으로도 충분히 알 수 있을것 같은데 filter 연산을 한 번 더 해야되는것 때문에 그런가 싶기도하고... ReviewPolicy이지 ReviewImagePolicy가 아니여서 그런가? 싶기도 하고... 혼자서는 도저히 결론을 내지 못하겠어서 도움을 청하게 되었습니다 ㅠㅠ 늘 좋은 강의 정말 감사드리고, 추석 잘 보내세요!
SELECT m.member_id, m.member_name, m.grade, COUNT(o.order_id) AS order_count, SUM(o.total_price) AS total_spent FROM member m JOIN orders o ON m.member_id = o.member_id WHERE m.grade = 'VIP' GROUP BY m.member_id, m.member_name, m.grade ORDER BY total_spent DESC LIMIT 20; 안녕하세요! 해당 쿼리에서는 group by 순서가 member_id, member_name, grade 순으로 되어있습니다. 강의에서는 group by 는 그룹핑을 할때 (member_id, member_name, grade) 을 기준으로 그룹핑 하여 순서가 상관없지만 인덱스 순서를 GROUP BY 순서에 맞게 인덱스를 설계 해야한다고 하셨습니다. grade 는 where 절에서 vip 상수로 필터링 하므로 인덱스에서 가장 왼쪽(앞)에 와야하지만 왜 member_id, member_name 순서에 맞게 인덱스를 줘야하는지 잘 모르겠습니다. 실제로 (grade, member_name, member_id) 순서로 member 테이블에 인덱스를 주고 EXPLAIN ANALZYZE 를 해보니 Aggregate using temporary table (actual time=373..373 rows=59999 loops=1) 가 나오는것을 확인했습니다. 임시테이블을 만들지 말지의 기준은 GROUP BY 로 그룹핑 하는 대상들이 연속적으로 올 경우는 굳이 임시테이블을 만들 필요가 없다는것으로 이해를 했습니다.(순서대로 오니까 미리 저장할 필요가 없으므로) 하지만 인덱스를 (grade, member_name, member_id) 순서로 줄 경우도 결국 인덱스 Grouping 순서에 맞게 오니까 임시테이블을 만들 필요가 없으니까 using temporary table 역시 발생하지 않아야 하는거 아닌가요? 그리고 설령 (grade, member_name, member_id) 로 주지 않고 (grade, member_name) 로 member테이블에 인덱스를 걸더라도 되는거 아닌가요? 어차피 세컨더리 인덱스 리프노드에는 member_id (pk) 가 선행컬럼을 기준으로 정렬되어 존재하니깐용 감사합니다!
안녕하세요. 강사님 강사님께서 26강 5일 가중이동평균 문제풀이 해주신 방법외에 아래와 같이 lag 함수 활용해서 문제 풀어도 현업에서 사용하기 문제 없을까요? with temp_01 as (select a.order_date as d_day, sum(b.amount) as sum_amount , row_number() over(order by date(a.order_date) asc) as rnum from nw.orders a join nw.order_items b on a.order_id = b.order_id where a.order_date >= date('1996-07-08') group by a.order_date) , temp_02 as ( select * , count(*) over(order by d_day rows between 4 preceding and current row) as cnt , avg(sum_amount) over(order by d_day rows between 4 preceding and current row) as m_avg_5days #일반 이동평균 구하기 , ( lag(sum_amount,1) over(order by d_day) * 1 + lag(sum_amount,2) over(order by d_day) * 1 + lag(sum_amount,3) over(order by d_day) * 1 + lag(sum_amount,4) over(order by d_day) * 0.5 + sum_amount * 1.5 ) / 5 as w_m_avg_5days #5일 가중이동평균 구하기 from temp_01 order by d_day ) select * from temp_02 where rnum >= 5; 이런식으로 풀어도 괜찮을까요? 현업에서 활용할때 어떤 방식이 더 효율적일지 궁금합니다!
강의에서 핸드폰 해상도 대응을 위해 Canvas의 Render Mode를 Screen Space - Camera로 설정하는 방법을 설명해주셨는데, 이 부분에 대해 궁금한 점이 있습니다. 현재 3D 게임을 제작하면서 Main Camera에 Post Processing을 적용하고 있는데, Screen Space - Camera 방식의 Canvas를 사용할 경우 UI가 Post Processing의 영향을 받을 수 있어서, Post Processing을 적용하지 않는 UI 전용 Overlay Camera를 따로 생성한 뒤 Main Camera의 Camera Stack에 추가하는 방식으로 처리하고 있습니다. 그런데 Canvas가 많아질수록 UI용 Camera와 Camera Stack을 계속 관리해야 해서 구조가 복잡해지는 문제가 있었습니다. 그래서 일반적인 HUD, 팝업, 메뉴 등의 UI는 Screen Space - Overlay로 변경하고, Canvas의 Sorting Order를 이용해 UI 간의 렌더링 순서를 관리하는 방식으로 바꿔도 괜찮을지 고민하고 있습니다. 혹시 강의에서 Canvas의 Render Mode를 Screen Space - Camera로 설정하도록 안내해주신 특별한 이유나, 모바일 게임에서 Screen Space - Overlay 대신 Screen Space - Camera를 사용하는 것이 더 유리한 경우가 있다면 설명 부탁드립니다. 감사합니다!
DB 쿼리를 설계하면서 항상 궁금했던 점이 있습니다. 쿼리가 점점 복잡해지다 보면 Sort , GROUP BY 등의 연산을 DB에서 처리하는 것보다, 데이터를 애플리케이션으로 가져온 후 애플리케이션에서 처리하는 것이 더 효율적이지 않을까 하는 생각이 들 때가 있습니다. 그렇다면 일반적으로 DB 쿼리를 최적화할 때는 애플리케이션으로 데이터를 가져와 처리하기보다는, 적절한 Index 설계를 통해 가능한 한 DB에서 연산을 처리하는 것이 맞는 방향일까요? 아니면 상황에 따라서는 필요한 데이터를 DB에서 조회한 후, 일부 연산을 애플리케이션에서 처리하는 것도 하나의 최적화 방법이 될 수 있을까요? 제가 생각하는 방향 자체가 잘못된 것인지, 아니면 실제로 상황에 따라 고려할 수 있는 방법인지 궁금해서 질문드립니다.
안녕하세요 영한님! 강의에서 말씀해 주신 것처럼, 인덱스를 생성한다고 해서 항상 옵티마이저가 해당 인덱스를 사용하는 것은 아니라는 점은 이해했습니다. 그렇다면 실무에서는 특정 인덱스를 어떤 쿼리나 사용 패턴을 고려해서 만들었는지, 그리고 어떤 의도로 설계했는지를 별도로 기록하거나 관리하는 방법이 있을까요? 예를 들어 시간이 지나 다른 개발자가 인덱스를 보더라도, “이 인덱스는 특정 조회 쿼리의 성능을 개선하기 위해 만들었다”와 같은 설계 의도를 파악할 수 있도록 관리하는지가 궁금합니다. 설계 1편에서 소개해 주신 용어 사전처럼 별도의 문서나 규칙을 두고 관리하는 방법이 있는지, 혹은 실무에서 일반적으로 사용하는 다른 방법이 있는지도 궁금합니다!
안녕하세요! product_id를 집계 기준으로 하는 GROUP BY 구문을 작성할 때, 해당 product_id와 맵핑되는 category_id은 SELECT절에서 max(category_id)으로 처리하는 방식으로 설명해주셨습니다. 혹시 아래처럼 category_id도 GROUP BY에 같이 작성한다면, 어떤 점이 다르며 이슈나 문제가 될만한 상황이 있는지 궁금합니다! SELECT a.PRODUCT_ID, b.CATEGORY_ID, sum(amount) AS sum_by_prod FROM nw.ORDER_ITEMS a JOIN nw.PRODUCTS b ON a.PRODUCT_ID = b.PRODUCT_ID GROUP BY a.PRODUCT_ID, b.CATEGORY_ID
현재 Controller 클래스는 온전히 순수하지 않다(9강 11:51)고 말씀해주셨는데 온전히 순수한 Controller 클래스는 어떤 형태여야 하는지가 궁금합니다. 제가 봤을때는 지금 Controller 가 프레젠테이션 레벨의 productAssembler 를 호출해서 포맷팅만 바꿔서 내려주고 있기 때문에 로직적인 부분이 클래스에 없어서 순수해보이는데요. 혹시 productAssembler 에서 isUnique 를 계산해주고 있어서 순수하지 않다고 표현하신 걸까요?? 어디서 타협을 하셨다는건지 잘 이해가 되지 않아서 설명해주시면 감사하겠습니다!
[질문 내용] 여기에 질문 내용을 남겨주세요. 저는 1번문제에서 FK -> PK 로풀었습니다 영한님은 PK -> FK 로 푸셨던것에 질문입니다. FK -> PK는 항상 다대일으로 e.managed_id가 가리키는 PK 행은 0~1개라서 조인해도 왼쪽 테이블 행이 늘지 않아서 왼쪽 테이블이 행을 정하고, 조인은 컬럼만 붙인다고 생각했습니다. PK -> FK는 일대로써 한 행이 여러 행으로 늘어나는데, 그럼 on 조건까지 다 읽어야 이해되지 않을까 해서 여쭤봅니다. select e.employee_id, e.name, e.managed_id, m.name as manager_name from employees e join employees m on e.managed_id = m.employee_id where m.name = '최과장';
안녕하세요 선생님, 좋은 강의 잘 수강하고 있습니다. 다름이 아니라 실습 환경 세팅 중에 막히는 부분이 있어서 문의를 남기게 되었습니다. 제가 현재 개인 PC가 아닌 회사 노트북을 사용하여 실습을 진행하려다 보니, 사내 보안 및 권한 문제로 인해 로컬에 PostgreSQL을 설치할 수가 없는 상황입니다. 현재 DBeaver를 통해 사내 시스템인 Hive DB에만 접근이 가능 합니다. 제공해 주신 실습 파일( data_schema.backup )을 확인해 보았는데, 해당 파일은 PostgreSQL 전용 백업 파일이라서 제가 사용하는 Hive 환경에서는 복원(Restore)을 하거나 데이터를 읽어 들일 수가 없습니다. 강의를 계속 따라가고 싶은데, 혹시 이 백업 파일 대신 아래 두 가지 형태의 파일을 별도로 제공해 주실 수 있으실까요? 로우 데이터 파일: 엑셀이나 텍스트 형태의 원본 데이터 파일 (예: .csv 또는 .txt ) 스키마 쿼리 파일: 각 테이블의 컬럼명과 데이터 타입을 알 수 있는 테이블 생성 스크립트 (예: CREATE TABLE 문이 적힌 .sql 또는 텍스트 파일) CSV 파일과 테이블 생성 쿼리만 제공해 주시면, 제가 Hive 문법에 맞게 데이터 타입(예: VARCHAR -> STRING 등)을 직접 수정하여 테이블을 생성한 뒤 DBeaver의 데이터 Import 기능으로 밀어 넣어서 실습을 진행해 보겠습니다. 환경이 달라 번거로운 요청을 드리게 되어 죄송합니다. 확인해 주시면 정말 감사하겠습니다!
안녕하세요, sakila실전 17번에서 궁금증이 생겼는데요, store 테이블에 manager_staff_id가 있고, staff에 저는 staff_id만 존재해가지고 manager_staff_id가 staff_id안에 있을거라고 판단하고 join을 staff와 store로 하였습니다. 그래서 간단히 풀기는 하였는데 현업에서도 혹시 이와 같은 경우가 발생할 경우, 분석가가 판단하고서 join을 진행하는게 맞는건가요? 아니면 유관 부서에 질문해서 두 테이블에 있는 내용이 같은지 다른지를 묻고 진행하는게 맞는건가요?
안녕하세요 영한님, 영한님의 강의로 열심히 학습중인 학생입니다! 실전 진단 - 해결 방안2에서 복합인덱스 관련해 궁금증이 있습니다. 영한님의 강의에서는 (category_id, product_status, created_at)을 복합인덱스로 설정하셨는데, (category_id, created_at)을 복합인덱스로 설정하는 것에 대해서는 어떻게 생각하시는지 궁금합니다. product_status = 'ACTIVE'의 비율이 전체 테이블에 비교했을 때 전체의 85%였고, 이 price 조건을 비교하기 위해 클러스터드 인덱스가 접근해 행 전체를 읽은 후 실행엔진에서 걸러야하는데, product_stauts = 'ACTIVE' 비율이 85%에 해당되기 때문에 높은 확률로 통과하다 보니 인덱스 효용이 떨어질 것 같다는 생각이 들었습니다. 그래서 해당 쿼리를 생각했을 때 product_status도 복합인덱스에 추가할만한 가치가 있을까? 라는 질문을 던졌을 때 (영한님이 말씀해주신 것 처럼, 인덱스도 결국 비용이니깐) 크게 와닿지 못 했는데, 이와 관련해서 영한님의 의견이 궁금합니다! (두 복합 인덱스의 실행 계획) -- (category_id, created_at) -> Limit: 20 row(s) (cost=75331 rows=20)(actual time=0.719..11.5 rows=20 loops=1) -> Filter: ((product.price between 10000 and 50000) and (product.product_status = 'ACTIVE')) (cost=75331 rows=4595) (actual time=0.718..11.5 rows=20 loops=1) -> Index lookup on product using idx_category_created_at (category_id=11) (cost=75331 rows=413612) (actual time=0.698..11.4 rows=48 loops=1) -- (category_id, product_status, created_at) -> Limit: 20 row(s) (cost=78697 rows=20)(actual time=0.6..9.07 rows=20 loops=1) -> Filter: (product.price between 10000 and 50000) (cost=78697 rows=38255) (actual time=0.593..9.06 rows=20 loops=1) -> Index lookup on product using idx_category_status_created_at (category_id=11, product_status='ACTIVE') (cost=78697 rows=344330) (actual time=0.581..9.03 rows=40 loops=1)
graphRAG - Neo4J로 구현하는 지식 그래프 기반 RAG 시스템 (feat. LangChain)
KG 구축 - 2) 뉴스 텍스트를 지식그래프로 변환 (LLMGraphTransformer 활용) 관련 질문. 강의의 9분 쯤에서, Person, NewsArticle이 기대와 달리 특정 값이 추출되지 않았다고 설명하셨는데, 이 두개 노드는 앞에서 constraint 를 등록할 때 포함된것 아닌가요? 저희가 허락한것은 allowed_nodes = ["Company", "Product", "Technology"] 이고요. LLM에서 이 2가지가 있는지 모를것 같은데요...