728x90
728x90
반응형
728x90

 

문제 : 백준 2884번 : 알람 시계 

2884번: 알람 시계 (acmicpc.net)

 

2884번: 알람 시계

상근이는 매일 아침 알람을 듣고 일어난다. 알람을 듣고 바로 일어나면 다행이겠지만, 항상 조금만 더 자려는 마음 때문에 매일 학교를 지각하고 있다. 상근이는 모든 방법을 동원해보았지만,

www.acmicpc.net

 

 

풀이 과정

문제 조건

  • 입력 첫 줄 : int 2ea
    • h : hour    0~23
    • m : minute  0~59
  • 시간표시 : 24시간 형태
    • 불필요한 0표시 x
  • 첫째 줄에 상근이가 창영이의 방법을 사용할 때, 설정해야 하는 알람 시간을 출력한다

brain Storming
입력된 설정 시간보다 시간이 빨라야함(값이 작아야함)
-45 한다고하면 hour가 -1되는 경우와 -1시가 되는 경우가 고려되어야함

 

 

일단 예제 입력 출력대로 해서 룩은 똑같이 나오는데

공백도 한칸이고

근데 틀렸다고 나오는데 뭐가 문제인지 파악 중

BufferedReader br = new BufferedReader(new InputStreamReader(System.in));
        StringTokenizer st = new StringTokenizer(br.readLine(), " ");

        int hour = 0;
        int min = 0;

        while(st.hasMoreTokens()){
            hour = Integer.parseInt(st.nextToken());
            min = Integer.parseInt(st.nextToken());
        }
//        System.out.println("h = "+hour);
//        System.out.println("m = "+min);

        if((min-45) < 0 ){
            hour = hour-1;
            min = min - 45 + 60;
            if(hour < 0){
               hour = hour + 24;
            }
        }
        System.out.println(hour+" "+min);

 

 

 

 

 

728x90
반응형
728x90

 

 

 

application.yaml

  servlet:
    multipart:
      enabled: true
      max-file-size: 50MB
      location: /fileupload
      max-request-size: 50MB

 

input타입 file

name,id 속성 profileImage

lable태그 for속성 profileImage

<div class="row mb-3">
    <label for="profileImage" class="col-sm-2 col-form-label">프로필 사진</label>
    <div class="col-sm-10">
        <input type="file" class="form-control" 
            name="profileImage" id="profileImage" /> <!--  -->
    </div> 
</div>

 

submit 발생시 FormData 클래스를  사용해서 기존에 $form을 넣어주고

contentType: false,
processData: false를 해줘야  jQuery에서도 FormData를 서버로 전송이 가능
jQuery 내부적으로는  multipart/form-data 로 전송됨

// form을 핸들링 하기위해 for을 가져옴
var $form = $('#member-join-form'); // html 요소를 찾는 기능. 폼이 2개면 배열이 됨. 이때는 폼태그에 id속성줘서 구분시키면됨

$form.submit(function(){
    try {
        var formData = new FormData($form[0]);
        console.log('formData',formData);
        $.ajax({
            url: '/member/join',
            type: 'post',
            data: formData,
            contentType: false,
            processData: false,
            success: function(){ // success는 스프링으로 치면 controller 역할
                location.href = '/member/join-complete';
            },
            error: function(data){
                console.log(data);
                alert(data.responseJSON.message);
            }
        });
    } catch (e) {
        console.error(e);
    }
    // 페이지가 전환되지 않게 방지
    return false;
})

 

 

 

728x90
반응형
728x90

 

Spring Security의 디펜던시

<dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-security</artifactId>
</dependency>
<dependency>
    <groupId>org.thymeleaf.extras</groupId>
    <artifactId>thymeleaf-extras-springsecurity5</artifactId>
</dependency>
<dependency>
    <groupId>org.springframework.security</groupId>
    <artifactId>spring-security-test</artifactId>
    <scope>test</scope>
</dependency>

 

시큐리티 설정 클래스

@Configuration
@EnableWebSecurity
public class WebSecurityConfiguration {

	@Bean
	public SecurityFilterChain securityFilterChain(HttpSecurity http) throws Exception{
			http.authorizeRequests()
			// 해당 url 패턴은 로그인 권한 없어도 접근 되도록
			.antMatchers("/public/**", "/member/form", "/member/join**")
			.permitAll()
			// 나머지 요청은 로그인을 해야 접근 되도록
			.anyRequest().hasRole("USER").and()
			// .csrf().disable() : ?
			.formLogin()
			.permitAll();
			
		return http.build();
	}
	
	/**
	 * 비밀번호 인코더 등록
	 * 등록안하면 There is no PasswordEncoder mapped for the id "null"에러가 발생함
	 * @return
	 */
	@Bean
	public PasswordEncoder passwordEncoder() {
		return new BCryptPasswordEncoder();
	}
	
	
}

 

MemberController에 추가한 내용

private final PasswordEncoder passwordEncoder;

String password = passwordEncoder.encode(form.getPassword());
// 암호화된 비밀번호로 저장
form.setPassword(password);

 

 

SecurityUserDetails implements UserDetails 생성

@Builder
@Data
public class SecurityUserDetails implements UserDetails{
	// 클래스명인 SecurityUserDetails 빨간줄 명령어 add unimplemented method 하면
	//  Collection<? extends GrantedAuthority> getAuthorities()
	// isAccountNonExpired()
	// isAccountNonLocked()
	// isCredentialsNonExpired()
	// isEnabled()
	// 추가됨
	
	private final int memberSeq;
	private final String username;
	private final String password;
	private final String nickname;
	@Override
	public Collection<? extends GrantedAuthority> getAuthorities() {
		// 권한을 추가해줘야 로그인 이후 오류 발생x
		return Arrays.asList(new SimpleGrantedAuthority("ROLE_USER"));
	}
	@Override
	public boolean isAccountNonExpired() {
		return true;
	}
	@Override
	public boolean isAccountNonLocked() {
		return true;
	}
	@Override
	public boolean isCredentialsNonExpired() {
		return true;
	}
	@Override
	public boolean isEnabled() {
		return true;
	}
	
	
	
}

 

728x90
반응형
728x90

@ControllerAdvice

@Controller 어노테이션이 있는 모든 곳에서 예외처리 하는 기능

@ControllerAdvice 안에 있는 @ExceptionHandler는 모든 컨트롤러에서 발생하는 예외처리

@ControllerAdvice의 속성 설정을 통하여 원하는 컨트롤러나 패키지만 선택가능하며,

디폴트값은 모든 패키지에 있는 컨트롤러의 예외처리

 

@ExceptionHandler

특정 예외 클래스를 핸들링 가능하게 지원

@Controller , @RestController가 적용된 Bean 에서 발생하는 예외를 잡아서 하나의 메서드에서 처리해주는 기능

@ExceptionHandler에 설정한 예외가 발생하면 handler가 실행됨

@Controller, @RestController가 아닌 @Service나 @Repository가 적용된 Bean에서는 사용불가

 

@RestControllerAdvice

@ControllerAdvice + @ResponseBody → @RestControllerAdvice

@ControllerAdvice와 동일한 역할하나,

응답의 body에 객체를 넣어 반환이 가능

@RestControllerAdvice는 @RestController,  @Controller에서 발생하는 예외 모두 잡을 수 있다

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.web.bind.annotation.ControllerAdvice;
import org.springframework.web.bind.annotation.ExceptionHandler;
import org.springframework.web.servlet.ModelAndView;

@ControllerAdvice
public class ExampleControllerAdvice {

	final Logger logger = LoggerFactory.getLogger(getClass());
	
	
	/**
	 * Exception 발생에 대한 예외처리
	 * @param e
	 * @return
	 */
	
	@ExceptionHandler(Exception.class)
	public ModelAndView handleException(Exception e) {
		logger.error("handleException",e);
		ModelAndView model = new ModelAndView("/error/error.html");
		model.addObject("exception", e);
		return model;
		
	}
	
}

 

 

자료참조

https://tecoble.techcourse.co.kr/post/2021-05-10-controller_advice_exception_handler/

728x90
반응형
728x90

 

 

메인 메소드 설정된 클래스

 

Spring Boot 프로젝트에는  @SpringBootApplication 어노테이션이  적용된 class가 반드시 있어야하며
public static main 메소드를  구현하고  SpringApplication.run(현재 클래스)를 호출함으로서
내장 톰캣서버이 실행되면서 Spring Boot에서 제공하는 stater 라이브러리에 포함된 기본 설정이 자동으로  이루어지면서 서버 실행이 진행

import org.mybatis.spring.annotation.MapperScan;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;

@SpringBootApplication(scanBasePackages = "com.example")
@MapperScan("com.example.mapper")
public class JavaWeb06SpringBootApplication {

	public static void main(String[] args) {
		SpringApplication.run(JavaWeb06SpringBootApplication.class, args);
	}

}

 

728x90
반응형
728x90

 

<dependencies>와 <build> 직접 쳐보면서

안에 뭐가 있는데 내부태그로는 뭐가 있는지 알아 보는 시간이었음

spring-core, spring-beans, spring-web,webmvc 등등 구성들이 눈에 많이 익게되었다!

 

<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/maven-v4_0_0.xsd">
<modelVersion>4.0.0</modelVersion>
<groupId>com.example</groupId>
<artifactId>java-web-03-spring2x</artifactId>
<packaging>war</packaging>
<version>0.0.1-SNAPSHOT</version>
<name>java-web-03-spring2x Maven Webapp</name>
<url>http://maven.apache.org</url>

<dependencies>
    <!-- https://mvnrepository.com/artifact/org.springframework/spring-core -->
    <dependency>
        <groupId>org.springframework</groupId>
        <artifactId>spring-core</artifactId>
        <version>2.0.8</version>
        <exclusions>
            <exclusion>
                <groupId>javax.servlet</groupId>
                <artifactId>servlet-api</artifactId>
            </exclusion>
        </exclusions>
    </dependency>

    <dependency>
        <groupId>org.springframework</groupId>
        <artifactId>spring-context</artifactId>
        <version>2.0.8</version>
    </dependency>

    <dependency>
        <groupId>org.springframework</groupId>
        <artifactId>spring-beans</artifactId>
        <version>2.0.8</version>
    </dependency>

    <dependency>
        <groupId>org.springframework</groupId>
        <artifactId>spring-web</artifactId>
        <version>2.0.8</version>
    </dependency>

    <dependency>
        <groupId>org.springframework</groupId>
        <artifactId>spring-webmvc</artifactId>
        <version>2.0.8</version>
    </dependency>

    <dependency>
        <groupId>org.springframework</groupId>
        <artifactId>spring-jdbc</artifactId>
        <version>2.0.8</version>
    </dependency>

    <dependency>
        <groupId>org.springframework</groupId>
        <artifactId>spring-orm</artifactId>
        <version>1.2.9</version>
    </dependency>	

    <!-- https://mvnrepository.com/artifact/org.apache.ibatis/ibatis-core -->
    <dependency>
        <groupId>org.apache.ibatis</groupId>
        <artifactId>ibatis-core</artifactId>
        <version>3.0</version>
    </dependency>

    <!-- https://mvnrepository.com/artifact/org.apache.ibatis/ibatis-sqlmap -->
    <dependency>
        <groupId>org.apache.ibatis</groupId>
        <artifactId>ibatis-sqlmap</artifactId>
        <version>2.3.0</version>
    </dependency>		

    <!-- https://mvnrepository.com/artifact/mysql/mysql-connector-java -->
    <dependency>
        <groupId>mysql</groupId>
        <artifactId>mysql-connector-java</artifactId>
        <version>5.1.49</version>
    </dependency>

    <!-- https://mvnrepository.com/artifact/log4j/log4j -->
    <dependency>
        <groupId>log4j</groupId>
        <artifactId>log4j</artifactId>
        <version>1.2.16</version>
    </dependency>

    <!-- https://mvnrepository.com/artifact/commons-dbcp/commons-dbcp -->
    <dependency>
        <groupId>commons-dbcp</groupId>
        <artifactId>commons-dbcp</artifactId>
        <version>1.2.2</version>
    </dependency>

    <!-- https://mvnrepository.com/artifact/org.apache.taglibs/taglibs-standard-impl -->
    <dependency>
        <groupId>org.apache.taglibs</groupId>
        <artifactId>taglibs-standard-impl</artifactId>
        <version>1.2.1</version>
        <scope>runtime</scope>
    </dependency>

    <!-- https://mvnrepository.com/artifact/javax.servlet/servlet-api -->
    <dependency>
        <groupId>javax.servlet</groupId>
        <artifactId>servlet-api</artifactId>
        <version>2.5</version>
        <scope>provided</scope>
    </dependency>

    <!-- https://mvnrepository.com/artifact/javax.servlet/jstl -->
    <dependency>
        <groupId>javax.servlet</groupId>
        <artifactId>jstl</artifactId>
        <version>1.2</version>
    </dependency>		


    <dependency>
        <groupId>junit</groupId>
        <artifactId>junit</artifactId>
        <version>3.8.1</version>
        <scope>test</scope>
    </dependency>
</dependencies>



<build>
<finalName>java-web-03-spring2x</finalName>
</build>


</project>

 

 

728x90
반응형
728x90

 

Properties prop = new Properties();

key와 value를 String으로 제한시켜놓은 Map구조의 컬렉션

Properties pro = new Properties();
pro.setProperty("a","aa");
pro.setProperty("b","bb"); // setProperty는 str만 받음
pro.put("c","cc");         // put은 object를 받음

System.out.println("pro : "+pro); // {b=bb, a=aa, c=cc} : map은 순서x

pro.getProperty("a"); // getProperty는 String만 취급
pro.get("b"); // get은 object를 받음
System.out.println(pro.getProperty("a")); // aa
System.out.println(pro.get("b"));   // bb -> 해당 key의 value값 출력됨
pro.remove("c");
System.out.println(pro); // {b=bb, a=aa}

 

1.HashMap put(K key, V value):V

반환타입 : value

HashMap<String,Snack> hmap = new HashMap<>();
hmap.put("A", new Snack("짠맛",100)); // list add랑 다르게 put으로 추가
hmap.put("B",new Snack("단맛",100));
System.out.println(hmap); // {A=Snack{flavor='짠맛', price=100}, B=Snack{flavor='단맛', price=100}}
// Map은{key=value}으로 출력됨
// 구분자로 나눠서 뭔가 해볼 수 있을 듯?

 

2.containsKey(Object key) 키나 값이 들어가 있는지를 확인하는 메소드

containsKey(Object key):boolean

containsValue(Object value):boolean

hmap.containsKey("A");
System.out.println(hmap.containsKey("A")); /// true
System.out.println(hmap.containsValue(new Snack("단맛",100)));

 

3.get() get(Object key) : v

key값에 맞는 'value값 반환'

hmap.get("B");
System.out.println(hmap.get("A")); // Snack{flavor='짠맛', price=100}

 

4-1.remove(Object key):V
4-2.remove(Object key, Object value):default boolean

System.out.println(hmap.remove("B")); // Snack{flavor='단맛', price=100}
System.out.println(hmap); // {A=Snack{flavor='짠맛', price=100}} 남은 값

 

전체코드

        // Properties prop = new Properties();
        // key와 value를 String으로 제한시켜놓은 Map구조의 컬렉션

        Properties pro = new Properties();
        pro.setProperty("a","aa");
        pro.setProperty("b","bb"); // setProperty는 str만 받음
        pro.put("c","cc");         // put은 object를 받음

        System.out.println("pro : "+pro); // {b=bb, a=aa, c=cc} : map은 순서x

        pro.getProperty("a"); // getProperty는 String만 취급
        pro.get("b"); // get은 object를 받음
        System.out.println(pro.getProperty("a")); // aa
        System.out.println(pro.get("b"));   // bb -> 해당 key의 value값 출력됨
        pro.remove("c");
        System.out.println(pro); // {b=bb, a=aa}


        // 1.HashMap
        // put(K key, V value):V
        // 반환타입 : value
        HashMap<String,Snack> hmap = new HashMap<>();
        hmap.put("A", new Snack("짠맛",100)); // list add랑 다르게 put으로 추가
        hmap.put("B",new Snack("단맛",100));
        System.out.println(hmap); // {A=Snack{flavor='짠맛', price=100}, B=Snack{flavor='단맛', price=100}}
        // Map은{key=value}으로 출력됨
        // 구분자로 나눠서 뭔가 해볼 수 있을 듯?

        // 2.containsKey(Object key)
        // 키나 값이 들어가 있는지를 확인하는 메소드
        // containsKey(Object key):boolean
        // containsValue(Object value):boolean
        hmap.containsKey("A");
        System.out.println(hmap.containsKey("A")); /// true
        System.out.println(hmap.containsValue(new Snack("단맛",100)));


        // 3.get()
        // get(Object key) : v
        // key값에 맞는 'value값 반환'
        hmap.get("B");
        System.out.println(hmap.get("A")); // Snack{flavor='짠맛', price=100}

        // 4-1.remove(Object key):V
        // 4-2.remove(Object key, Object value):default boolean
        System.out.println(hmap.remove("B")); // Snack{flavor='단맛', price=100}
        System.out.println(hmap); // {A=Snack{flavor='짠맛', price=100}} 남은 값

        // 5.keySet() & entrySet()
        // keySet()
        // keySet():Set<K>
        // 맵에 있는 key들을 set에 담아 반환

        // 방법1
        hmap.keySet();
        System.out.println(hmap.keySet()); // [A]

        // 방법2
        // set의 [] 없이 안에 값만 뽑고 싶다면 방법2 사용
        // Set객체 생성하여 map의 keySet()를 넣어주고 이를 다시 Iterator에 넣어서
        // while + hasNext()로 읽어들인다.
        // set이기 때문에 찍으면 기본적으로 key값이 나옴
        // value값을 읽어오고 싶다면 원본 데이터인 map에서 get()를 통해 끌어오면된다
        Set<String> set = hmap.keySet();
        Iterator<String> it = set.iterator();
        while(it.hasNext()){
            String str = it.next();
            System.out.println("String : "+str+" // hmap.get(a) : "+hmap.get(str));
            // a : A // hmap.get(a) : Snack{flavor='짠맛', price=100}
        }



        // entrySet()
        // entrySet():Set<Map.Entry<K,V>>
        // map에 있는 entry들을 set 담에 반환(키와 값의 쌍을 set에 담아 반환)
        // entry 의미 : 키와 값을 묶은 것(키와 값의 쌍)

        // 방법1
//        System.out.println(hmap.entrySet());//[사과류=아오리[200원], 참외류=참외[300원]]
        hmap.entrySet();
        System.out.println(hmap.entrySet()); // [A=Snack{flavor='짠맛', price=100}]

        hmap.put("B",new Snack("단맛",100));
        System.out.println(hmap.entrySet());
        // [A=Snack{flavor='짠맛', price=100}, B=Snack{flavor='단맛', price=100}]


        // 방법2
        // set의 [] 없이 안에 값만 뽑고 싶다면 방법2 사용
        Set<Map.Entry<String,Snack>> setEnt = hmap.entrySet();
        Iterator<Map.Entry<String,Snack>> iter = setEnt.iterator();
        while(iter.hasNext()){
            Map.Entry<String,Snack> ent = iter.next();
            System.out.println(ent); // A=Snack{flavor='짠맛', price=100} B=Snack{flavor='단맛', price=100}
            System.out.println(ent.getValue()); // Snack{flavor='짠맛', price=100} Snack{flavor='단맛', price=100}
        }

        // size():int
        hmap.size();
        System.out.println(hmap.size()); // 2


        // TreeMap
        // 정렬 가능
        // putAll()
        // putAll(Map<? extends K,? extends V> m):void
        // 다른 맵의 값을 추가

        TreeMap<String,Snack> tmap = new TreeMap<>(hmap);
        System.out.println(tmap); // {A=Snack{flavor='짠맛', price=100}, B=Snack{flavor='단맛', price=100}}
        tmap.put("C",new Snack("신맛",100));
        tmap.put("D",new Snack("쓴맛",100));
        System.out.println(tmap);
        // {A=Snack{flavor='짠맛', price=100}, B=Snack{flavor='단맛', price=100}, C=Snack{flavor='신맛', price=100}, D=Snack{flavor='쓴맛', price=100}}
        // A,B,C,D 정렬되서 나옴

        // remove(Object key):V
        // remove(Object key, Object value):boolean
        System.out.println(tmap.remove("D")); // Snack{flavor='쓴맛', price=100}
        System.out.println(tmap.remove("C",new Snack("신맛",100))); // true
        System.out.println(tmap); // {A=Snack{flavor='짠맛', price=100}, B=Snack{flavor='단맛', price=100}}

        // replace(K key, V oldValue, V newValue):boolean
        tmap.replace("B",new Snack("단맛",100),new Snack("뉴",10));
        System.out.println(tmap);
        // {A=Snack{flavor='짠맛', price=100}, B=Snack{flavor='뉴', price=10}}
        // b의 밸류값인 snack의 맛과 가격이 변경됨
        tmap.replace("B",new Snack("뉴뉴",10000));
        System.out.println(tmap);
        // {A=Snack{flavor='짠맛', price=100}, B=Snack{flavor='뉴뉴', price=10000}}

 

728x90
반응형
728x90
인텔리제이에서 돌리면 작동 잘하는데 백준에서 런타임 에러 (NoSuchElement) 발생

 

BufferedReader br = new BufferedReader(new InputStreamReader(System.in));
StringTokenizer st = new StringTokenizer(br.readLine(),",");


int x = 0;
int y = 0;
while(st.hasMoreTokens()){
    x = Integer.parseInt(st.nextToken());
    y = Integer.parseInt(st.nextToken());
}

System.out.println(x);
System.out.println(y);

if( x > 0 && y > 0){
    System.out.print(1);
}else if(x < 0 && y > 0){
    System.out.print(2);
}else if( x < 0 && y < 0){
    System.out.print(3);
}else if(x > 0 && y < 0){
    System.out.print(4);
}else{
    System.out.print("잘못 입력 되어있습니다");
}
728x90
반응형
728x90

 

값을 입력 받을 때, 

특정 조건의 값을 받고 싶지 않거나 특정 값만 받고 싶을 때

반복문 + if문

반복문 안에 조건문을 넣어서 반복시키면서 if문 안에서 해당 조건이 만족하면

true 조건에 해당 값을 변수에 넣어서 저장하는 방식으로 받으면 된다

 

ex)

int x = 0;
int y = 0;
for(int i=1; i <=2; i++) {
    if(x!=0 && y!=0) {
       x = Integer.parseInt(br1.readLine());
       y = Integer.parseInt(br2.readLine());
    }
}

 

728x90
반응형

+ Recent posts