묻고 답해요
164만명의 커뮤니티!! 함께 토론해봐요.
인프런 TOP Writers
-
미해결자바 ORM 표준 JPA 프로그래밍 - 기본편
OneToMany에서 LazyLoading 관련 질문이 있습니다.
Member : Team = N : 1 관계에서 Team 엔티티에서 @OneToMany(fetch = FetchType.LAZY)로 Member를 참조하고 있는 상황입니다. Team team = TeamRepository.findById(1L);team.getMembers().get(0)를 한 후 쿼리를 보니 다음과 같이 나가는 것을 볼 수 있었습니다 (member엔 id, name, team_id column만 존재합니다)제 생각으론 id, name, team_id만 조회해오면 될 것 같은데 추가적인 team_id, id 조회가 중복으로 나가고있는데 이유가 무엇일까요? ㅠㅠ 도저히 해결이 안돼서 질문올려요..
-
미해결파이썬 알고리즘 문제풀이 입문(코딩테스트 대비)
아니그램 질문입니다!
a = input() b = input() c = dict() for x in a: c[x] = c.get(x, 0) + 1 for x in b: c[x] = c.get(x, 0) -1 for val in c.values(): if val != 0: print("NO") break else: print("YES")선생님 안녕하세요!위 코드처럼 각 밸류의 값 중에 0이 아닌 값이 있다면바로 No 출력하는것도 괜찮을까요?돌려봤을 때 문제 없었습니다! 항상 감사합니다!
-
미해결[리뉴얼] Node.js 교과서 - 기본부터 프로젝트 실습까지
hashtag set 구현 질문
const arr_hash = req.body.content.match(/#[^\s#]/g); const hash_set = new Set(arr_hash) const hashtags = new Array() hash_set.forEach((element) => { hashtags.push(element); }) if (hashtags) { const result = await Promise.all( hashtags.map(tag => { return Hashtag.findOrCreate({ where: { title: tag.slice(1).toLowerCase() }, }) }), ); await post.addHashtags(result.map(r => r[0])); }hashtag를 set으로 만들기 위해서 이렇게 코드를 만들었는데 이렇게 만드니까데이터 베이스에 이런식으로 글자가 하나만 찍혀서 저장이 됩니다 어떻게 해야하나요?
-
미해결애플 웹사이트 인터랙션 클론!
코드 이름 검색해서 찾아가는 거 혹시 이름 알 수 있을까욤??
코드 이름 검색해서 찾아가는 거 혹시 이름 알 수 있을까욤??
-
미해결Spring Cloud로 개발하는 마이크로서비스 애플리케이션(MSA)
docker로 mariadb배포 시 문제 발생
현재 증상입니다.환경은 windows10입니다. mariadb를 켰을 때사진이 잘 안 보일 수 있어서 에러 메세지를 아래 써놨습니다.PS C:\Users\ccro1> docker run -d -p 3306:3306 --network ecommerce-network --name mariadb ccro1307/test:mariadb 33de5e6b75944d49e8e4220d428d0674d90103f4719387db1f566e7c927429e8 docker: Error response from daemon: Ports are not available: exposing port TCP 0.0.0.0:3306 -> 0.0.0.0:0: listen tcp 0.0.0.0:3306: bind: Only one usage of each socket address (protocol/network address/port) is normally permitted. mariadb를 껐을 때껐을 때는 mysql이 없다고 그러고켰을 때는 port가 중첩되서 안된다는 것 같은데..해결책이 어떻게 될 까요 mariadb는.\bin\mariadb-install-db.exe --datadir=C:\Work\mariadb-10.5.17-winx64\data --service=mariaDB --port=3306 --password=test1357로 설치하였습니다.
-
미해결파이썬 알고리즘 문제풀이 입문(코딩테스트 대비)
교육과정 설계 질문입니다.
need = input() n = int(input()) for i in range(n): plan = input() imt = deque(need) for x in plan: if imt[0]==x: imt.popleft() if len(imt)==0: break if len(imt)==0: print("#%d YES" %(i+1)) else: print("#%d NO" %(i+1))안녕하세요 선생님!구현해봤는데 케이스2에서 오류가 나서요 ㅠ어떤 부분이 문제가 있을까요?? 좋은 강의 감사합니다!
-
미해결스프링 MVC 1편 - 백엔드 웹 개발 핵심 기술
FrontControllerServletV3에서 render방법
[질문 템플릿]1. 강의 내용과 관련된 질문인가요? (예)2. 인프런의 질문 게시판과 자주 하는 질문에 없는 내용인가요? (예)3. 질문 잘하기 메뉴얼을 읽어보셨나요? (예)[질문 내용]1. FrontControllerServletV3에서 createParamMap에서 모든 파라미터 값들을 가지고 온다고 설명해주셨는데, 어떤 값들을 가지고오는건지 알 수 있을까요?2. 그리고 render의 경우 modelView, request, response를 넘기는데, modelTpRequestAttribute에서 request에 모든 값을 담아놓는다고 했는데 물리경로도 들어가있는건가요? 그렇다면 어디서 model에 넣어준 것인지 알 수 있을까요?
-
미해결스프링 MVC 1편 - 백엔드 웹 개발 핵심 기술
new-form.jsp 요청 시 한글 깨짐
안녕하세요, '섹션3-JSP로 회원 관리 웹 애플리케이션 만들기' 실습 중 발생한 오류에 관해서 질문드립니다.new-form.jsp를 요청했을 때 new-form.jsp 파일이 다운로드 되는 문제를 겪어서 질문란에 있는 답변대로 서버 실행 시 나오는 톰캣 버전과 의존성 버전을 수동으로 맞춰주었는데요(스프링 부트 버전(2.7.4)은 건들지 않았습니다), 파일이 다운로드 되는 문제는 해결되었지만 이렇게 한글이 깨져서 나옵니다.. new-form.jsp에서 'charset=UTF-8'를 추가했는데도 아래 사진과 같이 나오는 이유가 무엇인지 잘 모르겠습니다.(html 파일에서는 한글이 깨지지 않고 제대로 나왔었습니다)
-
미해결스프링 핵심 원리 - 고급편
PostProcessor로 생성된 bean 의 type 은 Proxy 객체가 아닌가요?
[질문 내용]BeanPostProcessorTest.java 를 조금 수정하였는데요.AToBPostProcessor 에 if (bean instanceof A) 이면 ProxyFactory를 사용하여 proxy 객체를 리턴하도록 하였습니다. 그 후 테스트코드에서 applicationContext.getBean("beanA") 를 찍어보았더니, class.com.sun.proxy$Proxyxx 가 아닌 helloA 실제 객체가 찍혀있는걸 확인하였습니다. A a = applicationContext.getBean("beanA");a.helloA(); 하면 프록시가 잘 적용되서 부가기능이 찍히는걸 확인하였는데요. a 를 찍었을 때 Porxy 객체가 리턴될줄 알았는데 실 객체가 리턴되어서요. 왜 그런 것 일까요?
-
미해결실전! Querydsl
jpa 레포지토리 사용 중 오류
안녕하세요!querydsl과 jparepository 강의를 듣고 참고하여 개인 코딩 공부를 하고 있는 학생입니다.다름이 아니라 좋아요 기능 구현 중 customrepository를 사용하였는데 하단과 같은 오류가 발생해서 문의 드립니다.확인해보니 패키지를 분리하라고 하신 분도 있어서 패키지 분리를 했는데도 동일한 오류가 발생합니다ㅠ.ㅠ이유가 뭘까요..오류Error creating bean with name 'businessLikeService' defined in file [/Users/gimnayeon/Desktop/GreenProject/GrinGreen/out/production/classes/com/grin/GrinGreen/BusinessLike/service/BusinessLikeService.class]: Unsatisfied dependency expressed through constructor parameter 0; nested exception is org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'businessLikeRepository' defined in com.grin.GrinGreen.BusinessLike.repository.BusinessLikeRepository defined in @EnableJpaRepositories declared on JpaRepositoriesRegistrar.EnableJpaRepositoriesConfiguration: Invocation of init method failed; nested exception is org.springframework.data.repository.query.QueryCreationException: Could not create query for public abstract java.util.Optional com.grin.GrinGreen.BusinessLike.repository.BusinessLikeRepositoryCustom.exist(java.lang.String,java.lang.Long)! Reason: Failed to create query for method public abstract java.util.Optional com.grin.GrinGreen.BusinessLike.repository.BusinessLikeRepositoryCustom.exist(java.lang.String,java.lang.Long)! No property 'exist' found for type 'BusinessLike'!; nested exception is java.lang.IllegalArgumentException: Failed to create query for method public abstract java.util.Optional com.grin.GrinGreen.BusinessLike.repository.BusinessLikeRepositoryCustom.exist(java.lang.String,java.lang.Long)! No property 'exist' found for type 'BusinessLike'!BusinessLike Entity@Entity @Getter @NoArgsConstructor public class BusinessLike { @Id @GeneratedValue @Column(name = "like_id") private Long id; @ManyToOne(fetch = FetchType.LAZY) @JoinColumn(name = "mail") private Member member; @ManyToOne(fetch = FetchType.LAZY) @JoinColumn(name = "business_id") private Business business; @QueryProjection public BusinessLike(Member member, Business business) { this.member = member; this.business = business; } }BusinessLike DTO@Data public class BusinessLikeDto { private Member member; private Long businessId; @QueryProjection public BusinessLikeDto(Member member, Long businessId) { this.member = member; this.businessId = businessId; } }BusinessLike Response DTO@Data public class BusinessLikeResponseDto { private Long BusinessLikeNum; private Boolean check; @QueryProjection public BusinessLikeResponseDto(Long BusinessLikeNum, Boolean check) { this.BusinessLikeNum = BusinessLikeNum; this.check = check; } }BusinessLikeCustomRepositorypublic class BusinessLikeCustomRepositoryImpl implements BusinessLikeRepositoryCustom{ private final JPAQueryFactory queryFactory; public BusinessLikeCustomRepositoryImpl(EntityManager em) { this.queryFactory = new JPAQueryFactory(em); } @Override public Optional<BusinessLike> exist(String mail, Long businessId) { BusinessLike lList = queryFactory .selectFrom(businessLike) .where(businessLike.member.mail.eq(mail), businessLike.business.id.eq(businessId)) .fetchFirst(); return Optional.ofNullable(lList); } public long BusinessLikeNumfind(Long businessId) { return queryFactory .selectFrom(businessLike) .where(businessLike.business.id.eq(businessId)) .fetchCount(); } }BusinessLikeRepository@Transactional(readOnly = true) public interface BusinessLikeRepository extends JpaRepository<BusinessLike, Long>, BusinessLikeRepositoryCustom { }BusinessLikeRepositoryImplpublic interface BusinessLikeRepositoryCustom { Optional<BusinessLike> exist(String mail, Long businessId); long BusinessLikeNumfind(Long businessId); }BusinessLikeService@Slf4j @Service @Transactional @RequiredArgsConstructor public class BusinessLikeService { private final BusinessLikeRepository businessLikeRepository; private final BusinessRepository businessRepository; //좋아요 및 취소 public Boolean pushBusinessLike(BusinessLikeDto businessLikeDto) { businessLikeRepository.exist(businessLikeDto.getMember().getMail(), businessLikeDto.getBusinessId()) .ifPresentOrElse(businessLike -> businessLikeRepository.deleteById(businessLikeDto.getBusinessId()), ()-> { Business business = getBusiness(businessLikeDto); businessLikeRepository.save(new BusinessLike(businessLikeDto.getMember(), business)); }); return true; } @Transactional(readOnly = true) private Business getBusiness(BusinessLikeDto businessLikeDto) { return businessRepository.findById(businessLikeDto.getBusinessId()) .orElseThrow(() -> new IllegalArgumentException("해당 게시글은 존재하지 않습니다.")); } // 좋아요 개수 @Transactional(readOnly = true) public BusinessLikeResponseDto getBusinessLikeInfo(BusinessLikeDto businessLikeDto) { long businessLikeNum = getBusinessLikeNum(businessLikeDto); boolean check = checkPushedLike(businessLikeDto); return new BusinessLikeResponseDto(businessLikeNum, check); } @Transactional(readOnly = true) public boolean checkPushedLike(BusinessLikeDto businessLikeDto) { return businessLikeRepository.exist(businessLikeDto.getMember().getMail(), businessLikeDto.getBusinessId()) .isPresent(); } @Transactional(readOnly = true) public long getBusinessLikeNum(BusinessLikeDto businessLikeDto) { return businessLikeRepository.BusinessLikeNumfind(businessLikeDto.getBusinessId()); } }BusinessLikeServiceTest @SpringBootTest @Transactional public class BusinessLikeServiceTest { @Autowired BusinessLikeService businessLikeService; @Autowired MemberService memberService; @Autowired BusinessService businessService; @Test public void 좋아요() throws Exception{ //given Member member = new Member(); member.setNickname("testMember"); member.setMail("testMember@test.com"); member.setPassword("test1234!"); member.setMember_type("B"); member.setMember_status("J"); member.setHint_password("hint_01"); member.setAnswer_password("answer"); member.setUpdated_at(now()); member.setCreated_at(now()); memberService.join(member); Member findMember = memberService.findOne(member.getMail()); Business business = new Business(); business.setBusinessName("테스트밥집"); business.setHomepage("test.com"); business.setPhone("010-1234-5678"); business.setAddress("제주특별자치도 제주시 첨단로 242"); business.setLng((float) 33.450701); business.setLat((float) 126.570667); business.setCreated_at(now()); business.setUpdated_at(now()); businessService.join(business); Business findBusiness = businessService.findOne(business.getId()); //when BusinessLikeDto businessLikeDto = new BusinessLikeDto(findMember,findBusiness.getId()); businessLikeService.pushBusinessLike(businessLikeDto); System.out.println("businessLikeDto = " + businessLikeDto.getBusinessId());; //then assertEquals(1,businessLikeService.getBusinessLikeInfo(businessLikeDto).getBusinessLikeNum()); } }
-
미해결스프링 배치
테이블 명세에 대해 의문사항이 있습니다.
안녕하세요 강사님좋은 강의에 먼저 감사의 말씀 드립니다.https://github.com/spring-projects/spring-batch/blob/main/spring-batch-core/src/main/resources/org/springframework/batch/core/schema-mysql.sql테이블을 생성하는 구문은 위 링크와 같은데,BATCH_JOB_INSTANCE와 BATCH_JOB_EXECUTION의 경우 일대다 비식별 관계인 것이 이해가 갑니다.하지만 BATCH_JOB_EXECUTION와 BATCH_JOB_EXECUTION_CONTEXT는식별관계임에도 불구하고 일대다로 구성되어 있네요.. (복합키도 아님)여기서 질문 있습니다.이렇게 테이블을 구성하면 실제로 BATCH_JOB_EXECUTION_CONTEXT에는 중복된 값이 들어갈 수 없어 일대다 관계가 성립하지 않는 것 아닌가요?BATCH_JOB_EXECUTION_PARAMS의 경우 기본키가 없는데 혹시 알려주실 수 있으실까요?
-
미해결Vue.js 중급 강좌 - 웹앱 제작으로 배워보는 Vue.js, ES6, Vuex
파일 저장? 관련 질문이 있습니다.
안녕하세요 기효님!저는 백엔드 개발자인데 혼자 만들어보고 싶은 사이드 프로젝트가 있어서 기효님 강의를 듣고 대부분의 프론트 기능을 구현했습니다!! 강의 너무 알차고 유익했습니다.한가지 질문이 있습니다.어느 시점부터 새로 만든 파일들이 npm run serve를 통해서 작동을 하지 않습니다. 예를 들어 오늘 SnackBar 컴포넌트가 필요해 작성했고, 연동된 git 에도 푸쉬해서 올렸습니다. 하지만 npm run serve 를 통해 서버를 띄워서 작동을 시키면 snackBar컴포넌트를 포함한 최근에 추가한 파일들이 정상작동이 안 됩니다. 정상적인 작동이 되는 컴포넌트와 파일들은 터미널에서 cmd+s 를 눌러서 저장을 하면 터미널이 새로고침 되듯이 변경사항을 저장해 반영됩니다. 아래 첫 사진에서 cmd+s 를 누르면 터미널이 새로고침 되듯이 다시 run 하며 두번째 사진 화면으로 가집니다.하지만 정상적인 작동이 되지 않는 컴포넌트들은 cmd+s 를 눌러도 전혀 반응이 없습니다. 즉, 첫번째 사진화면에서 터미널은 아무런 반응이 없습니다.혹시 어떤 이유일지 기효님은 아실까요 ?? 이게 설정문제인지 뭔지 감도 잘 안옵니다 ㅠㅠ
-
해결됨[리뉴얼] Node.js 교과서 - 기본부터 프로젝트 실습까지
공부방향과 진로에 대해서 질문 드립니다.
현재 안정적인 직장(공기업 사무직)을 가지고 있지만 우연한 계기로 개발에 흥미를 가져서 계속 공부하고 있습니다. 개발 공부하면서 스스로를 많이 돌아 본 결과 저는 개발하는게 너무 재밌고, 제 적성에도 맞습니다. 컴퓨터앞에 하루종일 앉아서 코딩하면 너무 재밌고 시간도 잘 갑니다.이전에 최상위권 대학 문과 학부를 졸업했지만, 작년에 방송대 컴퓨터과학과 편입하여 내년 2월 우수한 성적으로 졸업을 앞두고 있고, 정보처리기사 자격증도 취득했습니다. 현재는 잠깐 휴직하고 부트캠프에서 javascript 기반으로 공부하고 있습니다. 다만 나이가 좀 많습니다. 30대 중반... 개인적으로 프론트보다 백엔드쪽이 성향에 맞아서 백엔드 개발자로 취업하고싶지만, 취업이 안된다면 개인적으로 1인 앱개발, 1인 창업, 외주 웹 프로젝트 등으로 현재 회사를 다니면서 개발을 계속하고 싶습니다.그래서 한국에서 백엔드의 정석이라는 spring말고 제로초님 강좌 들으면서 javascript, node.js, next.js 등을 학습하기로 결정하고 계속 공부 중입니다.요약하자면 30대 중반 방송대 컴퓨터학과 졸업생이 node.js와 typescript, nest.js를 학습하면 백엔드 개발자로 신입 취업하는 것이 가능할까요? 아니면 취업이 아니라 다른 방향으로 이외로 눈을 돌려봐야 될까요? 제로초님의 생각은 어떤지 궁금합니다. [제로초 강좌 질문 필독 사항입니다]질문에는 여러분에게 도움이 되는 질문과 도움이 되지 않는 질문이 있습니다.도움이 되는 질문을 하는 방법을 알려드립니다.https://www.youtube.com/watch?v=PUKOWrOuC0c0. 숫자 0부터 시작한 이유는 1보다 더 중요한 것이기 때문입니다. 에러가 났을 때 해결을 하는 게 중요한 게 아닙니다. 왜 여러분은 해결을 못 하고 저는 해결을 하는지, 어디서 힌트를 얻은 것이고 어떻게 해결한 건지 그걸 알아가셔야 합니다. 그렇지 못한 질문은 무의미한 질문입니다.1. 에러 메시지를 올리기 전에 반드시 스스로 번역을 해야 합니다. 번역기 요즘 잘 되어 있습니다. 에러 메시지가 에러 해결 단서의 90%를 차지합니다. 한글로 번역만 해도 대부분 풀립니다. 그냥 에러메시지를 올리고(심지어 안 올리는 분도 있습니다. 저는 독심술사가 아닙니다) 해결해달라고 하시면 아무런 도움이 안 됩니다.2. 에러 메시지를 잘라서 올리지 않아야 합니다. 입문자일수록 에러메시지에서 어떤 부분이 가장 중요한 부분인지 모르실 겁니다. 그러니 통째로 올리셔야 합니다.3. 코드도 같이 올려주세요. 다만 코드 전체를 다 올리거나, 깃헙 주소만 띡 던지지는 마세요. 여러분이 "가장" 의심스럽다고 생각하는 코드를 올려주세요.4. 이 강좌를 바탕으로 여러분이 응용을 해보다가 막히는 부분, 여러 개의 선택지 중에서 조언이 필요한 부분, 제 경험이 궁금한 부분에 대한 질문은 대환영입니다. 다만 여러분의 회사 일은 질문하지 마세요.5. 강좌 하나 끝날 때마다 남의 질문들을 읽어보세요. 여러분이 곧 만나게 될 에러들입니다.6. 위에 적은 내용을 명심하지 않으시면 백날 강좌를 봐도(제 강좌가 아니더라도) 실력이 늘지 않고 그냥 코딩쇼 관람 및 한컴타자연습을 한 셈이 될 겁니다.
-
미해결[개정판] 딥러닝 컴퓨터 비전 완벽 가이드
선생님 안녕하세ㅛ
선생님 https://github.com/open-mmlab/mmdetection/issues/8834위와 같은 증상인것 같은데MMsegmentation 할때 ballon 데이터 학습시키는데 자꾸 멈추는것 같습니다.. 이부분이 더 고민인게 멈추는 것인지 학습을 하는 것이지 의문입니다 그래서 epoch 1로 해봤는데도.. 안되는 것 같아요..왜그런걸까요.. ㅠㅠ..
-
미해결리눅스 커맨드라인 툴 (Full ver.)
강사님한테 배운것들 맥 os 에서도 쓰임새있나요?
맥이랑 리눅스둘다 유닉스 계열이잔아요.로드맵 강의 따라가고 있는데요.맥os 에서 가르쳐 주신 명령어나 다른 내용들 공통분모인 부분이 있나요??.
-
미해결HTML+CSS+JS 포트폴리오 실전 퍼블리싱(시즌1)
custom.js 오류문제
처음에는 강의듣고 코드 쓰는데에 불편함이 없어서 사용했는데 계속 오류창이 뜨고 가끔 안되는 상황도 있어서 질문드립니다.
-
미해결홍정모의 따라하며 배우는 C언어
static 변수를 동적할당하면 free 해줘야 하나요?
static 변수는 프로그램 종료시에 할당해제 되므로 따라 free를 안해줘도 상관없지만 malloc 과 같이 메모리를 할당하여 사용하면 메모리 누수 방지를 위해 free를 해줘야 하는걸로 알고 있습니다. 여기서 궁금한 점이 static 변수를 동적할당하면 그건 free 를 해줘야 하나요??
-
해결됨설계독학맛비's 실전 FPGA를 이용한 HW 가속기 설계 (LED 제어부터 Fully Connected Layer 가속기 설계까지)
linux 관련 문의
안녕하세요! 1강이 아닌 바로 2강을 결제해서 vitis와 Vivado를 설치하여 강의를 듣고있는데 1강을 참고하여 따로 Linux 환경에서 Vitis를 다시 깔아야할까요? 아니면 그대로 진행해도될까요? 감사합니다
-
미해결
강의 리스트 좋아요 기능
나중에 또 보고싶은 강의를 저장해놓고 싶어서 강의 내 커리큘럼 리스트 안에도 좋아요 기능이 있으면 좋을것같습니다!
-
해결됨유니티 머신러닝 에이전트 완전정복 (기초편)
A2C 알고리즘을 드론 환경에 적용하려면
안녕하세요, 드론 환경에서 A2C 알고리즘을 적용해서 실험해보려고 합니다.환경에 맞게 적용을 하기 위해 state_size, action_size를 각각 9와 3으로 설정하고, 이 외에도 여러 부분을 수정하여 돌려 보려고 했는데 잘 안 되네요.get_action() 함수를 손보거나, preprocess를 하는 부분을 수정해주어야 할 것 같은데, 어떻게 해결해야 할지 잘 모르겠습니다.현재 상태에서는 다음과 같은 오류가 발생하고 있습니다.A2C.py의 코드는 아래와 같습니다.import numpy as np import datetime import platform import torch import torch.nn.functional as F from torch.utils.tensorboard import SummaryWriter from collections import deque from mlagents_envs.environment import UnityEnvironment, ActionTuple from mlagents_envs.side_channel.engine_configuration_channel\ import EngineConfigurationChannel # A2C를 위한 파라미터 값 세팅 state_size = 9 action_size = 3 load_model = False train_mode = True discount_factor = 0.9 learning_rate = 0.00025 run_step = 100000 if train_mode else 0 test_step = 10000 print_interval = 10 save_interval = 100 # VISUAL_OBS = 0 # GOAL_OBS = 1 # VECTOR_OBS = 2 # OBS = VECTOR_OBS # 유니티 환경 경로 game = "Drone" os_name = platform.system() if os_name == 'Windows': env_name = f"C:/Users/user/anaconda3/envs/mlagents/Drone_0427/Drone_1002_3.exe" elif os_name == 'Darwin': env_name = f"../envs/{game}_{os_name}" # 모델 저장 및 불러오기 경로 date_time = datetime.datetime.now().strftime("%Y%m%d%H%M%S") save_path = f"./saved_models/{game}/A2C/{date_time}" load_path = f"./saved_models/{game}/A2C/20210709235643" # 연산 장치 device = torch.device("cuda" if torch.cuda.is_available() else "cpu") print("CUDA is available" if torch.cuda.is_available() else "CPU is available") # A2C 클래스 -> Actor Network / Critic Network 정의 class A2C(torch.nn.Module): def __init__(self, **kwargs): super(A2C, self).__init__(**kwargs) self.d1 = torch.nn.Linear(state_size, 128) self.d2 = torch.nn.Linear(128, 128) self.pi = torch.nn.Linear(128, action_size) self.v = torch.nn.Linear(128, 1) def forward(self, x): x = F.relu(self.d1(x)) x = F.relu(self.d2(x)) return F.softmax(self.pi(x), dim=1), self.v(x) # A2CAgent 클래스 -> A2C 알고리즘을 위한 다양한 함수 정의 class A2CAgent(): def __init__(self): self.a2c = A2C().to(device) self.optimizer = torch.optim.Adam(self.a2c.parameters(), lr=learning_rate) self.writer = SummaryWriter(save_path) if load_model == True: print(f"... Load Model from {load_path}/ckpt ...") checkpoint = torch.load(load_path+'/ckpt', map_location=device) self.a2c.load_state_dict(checkpoint["network"]) self.optimizer.load_state_dict(checkpoint["optimizer"]) # 정책을 통해 행동 결정 def get_action(self, state, training=True): # 네트워크 모드 설정 self.a2c.train(training) #네트워크 연산에 따라 행동 결정 pi, _ = self.a2c(torch.FloatTensor(state).to(device)) action = torch.multinomial(pi, num_samples=1).cpu().numpy() return action def train_model(self, state, action, reward, next_state, done): state, action, reward, next_state, done = map(lambda x: torch.FloatTensor(x).to(device), [state, action, reward, next_state, done]) pi, value = self.a2c(state) # Value network with torch.no_grad(): _, next_value = self.a2c(next_state) target_value = reward + (1-done) * discount_factor * next_value critic_loss = F.mse_loss(target_value, value) #Policy network eye = torch.eye(action_size).to(device) one_hot_action = eye[action.view(-1).long()] advantage = (target_value - value).detach() actor_loss = -(torch.log((one_hot_action * pi).sum(1))*advantage).mean() total_loss = critic_loss + actor_loss self.optimizer.zero_grad() total_loss.backward() self.optimizer.step() return actor_loss.item(), critic_loss.item() # 네트워크 모델 저장 def save_model(self): print(f"... Save Model to {save_path}/ckpt ...") torch.save({ "network" : self.a2c.state_dict(), "optimizer" : self.optimizer.state_dict(), }, save_path+'/ckpt') # 학습 기록 def write_summray(self, score, actor_loss, critic_loss, step): self.writer.add_scalar("run/score", score, step) self.writer.add_scalar("model/actor_loss", actor_loss, step) self.writer.add_scalar("model/critic_loss", critic_loss, step) # Main 함수 -> 전체적으로 A2C 알고리즘을 진행 if __name__ == '__main__': # 유니티 환경 경로 설정 (file_name) engine_configuration_channel = EngineConfigurationChannel() env = UnityEnvironment(file_name=env_name, side_channels=[engine_configuration_channel]) env.reset() # 유니티 브레인 설정 behavior_name = list(env.behavior_specs.keys())[0] spec = env.behavior_specs[behavior_name] engine_configuration_channel.set_configuration_parameters(time_scale=12.0) dec, term = env.get_steps(behavior_name) # A2C 클래스를 agent로 정의 agent = A2CAgent() actor_losses, critic_losses, scores, episode, score = [], [], [], 0, 0 for step in range(run_step + test_step): if step == run_step: if train_mode: agent.save_model() print("TEST START") train_mode = False engine_configuration_channel.set_configuration_parameters(time_scale=1.0) #preprocess = lambda obs, goal: np.concatenate((obs*goal[0][0], obs*goal[0][1]), axis=-1) #state = preprocess(dec.obs[OBS]) #state = preprocess(dec.obs[OBS],dec.obs[GOAL_OBS]) state = dec.obs[0] action = agent.get_action(state, train_mode) action_tuple = ActionTuple() action_tuple.add_continuous(action) env.set_actions(behavior_name, action_tuple) env.step() dec, term = env.get_steps(behavior_name) done = len(term.agent_id) > 0 reward = term.reward if done else dec.reward next_state = term.obs[0] if done else dec.obs[0] score += reward[0] if train_mode: agent.append_sample(state[0], action[0], reward, next_state[0], [done]) # 학습 수행 actor_loss, critic_loss = agent.train_model() actor_losses.append(actor_loss) critic_losses.append(critic_loss) if done: episode += 1 scores.append(score) score = 0 # 게임 진행 상황 출력 및 텐서 보드에 보상과 손실함수 값 기록 if episode % print_interval == 0: mean_score = np.mean(scores) mean_actor_loss = np.mean(actor_losses) mean_critic_loss = np.mean(critic_losses) agent.write_summray(mean_score, mean_actor_loss, mean_critic_loss, step) actor_losses, critic_losses, scores = [], [], [] print(f"{episode} Episode / Step: {step} / Score: {mean_score:.2f} / " +\ f"Actor loss: {mean_actor_loss:.2f} / Critic loss: {mean_critic_loss:.4f}") # 네트워크 모델 저장 if train_mode and episode % save_interval == 0: agent.save_model() env.close()답변 주시면 감사하겠습니다!