지난 포스트의 내용은 다음과 같았다.
app.get('/products/:n' , function(req, res) {
console.log(req.params) // { n: '5'}
console.log(req.params.n) // '5'
})
req.params 는 object 자료형을 반환하고,
req.params.n은 string 자료형을 반환한다.
즉, req.params의 value 값은 무조건 문자열 자료형으로 들어간다는 것이다.
자바스크립트의 특성상, 숫자값이 string으로 표현되어 있다고 해도 숫자값과 비교가 가능하다.
ex)
// req.params.n 이 "5" 일 때,
if (req.params.n < 10 ) {
console.log("test")
}
// 결과 : test
하지만 이렇게 사용하기보다는 자료형을 Int로 바꾸어주는 것이 옳다.
그 이유는 다음의 예시에서 알 수 있다.
// req.params.n = "5"
myNum = req.params.n + 1
console.log(myNum)
// 결과 : "51"
string과 int형을 더하게 되면, 결과값이 string으로 반환되기 때문에,
예측한 값인 6이 아니라, 51이라는 엉뚱한 값이 나온다.
따라서, 우리가 n으로 쓰고자 하는 값의 자료형이 숫자라면 그에 맞게 자료형을 변환시켜 사용해야한다.
string -> number로 자료형을 바꾸는 방법은 2가지가 있다.
parseInt("123"); // 123
parseInt("10", 2); // 2
특징)
1) 값의 앞자리부터 읽어서, 숫자가 아닌 값이 나타나면 그 이후는 생략된다.
ex)
parseInt("123.45"); // 123
parseInt("123px"); // 123
parseInt("aaaa123"); // NaN
2) 진수 표현이 가능하다.
// 10 을 2진수값으로써 계산
parseInt("10", 2); // 2
특징)
1) 소수점 표현도 number 자료형으로 바꾸어준다.
Number("123.45"); // 123.45
2) 숫자가 아닌 값이 들어있으면 NaN을 반환한다.
Number("123px"); // NaN
Number(""); // NaN
3) Boolean 자료형도 숫자로 반환이 가능하다.
Number(true); // 1
Number(false); // 0
따라서 자료형을 변환할 때, 목적에 맞게 선택하여 사용한다.
req.params의 예제로써 유튜브를 살펴보자.
유튜브의 유튜버들 채널에 들어가면, 다음과 같은 URL형식으로 작성되어있다.
https://www.youtube.com/@채널이름
또한, 영상을 클릭하면, 다음과 같은 URL 형식으로 작성되어있다.
https://www.youtube.com/watch?v=비디오값
이러한 주소값을 가지는 예제를 만들기 위해 다음과 같은 코드를 작성했다.
app.get('/:name' , function(req, res){
const param = req.params
res.json({
channel : param.name
})
})
이렇게 작성한 뒤, express 모듈을 이용하여 서버를 작동시키고
해당 URL을 입력해보면
{channel : name명} 이 출력되는 것을 확인할 수 있다.
유튜브에서 영상을 보다보면 13:05 이런 식으로 타임라인이 달려있는 경우가 있다.
사용자가 해당 링크를 클릭하면 영상이 해당 시간으로 이동한다.
이 타임라인의 링크를 복사해서 살펴보면 다음과 같다.
https://www.youtube.com/watch?v=비디오값&t=시간초값s
즉, 여러 데이터 값을 주고자 할 때 ?이라는 쿼리스트링을 사용한다
그리고 코드상에서 ? 뒤의 값들을 불러올 땐 req.query 를 이용한다.
app.get('/watch?v=비디오값&t=시간초값s' , function(req, res){
const q = req.query
console.log(q)
})
/*
결과 :
q = {v = '비디오값' , t = '시간초값s'}
*/
결과값을 보면 예측할 수 있겠지만 값을 사용하고자 할 땐
q.v, q.t 로 불러올 수 있다.
하지만, 이렇게 작성하는 것보다 더욱 간결하게 작성할 수 있는데, 비구조화를 이용하는 것이다.
우리는 req.query가 { key1 : value1, key2 : value2 ... } 형태로 값을 반환하는 것을 알고 있다.
따라서 변수에 담을 때, 미리 { } 를 이용하여 바로 변수에 담을 수 있다.
예제를 보자.
app.get('/watch?v=비디오값&t=시간초값s' , function(req, res){
const { v , t } = req.query
console.log(v)
console.log(t)
})
이것을 객체의 비구조화라고 한다.
주의해야할 점은, req.query가 key로써 v, t 를 가지고 있는 것이기 때문에, {} 내부의 변수명도 이와 똑같이 지정해줘야 한다는 것이다.
객체뿐만이 아니라, 배열에도 비구조화를 적용할 수 있다. 조금의 차이점이 있긴 하다.
const array = [0,1,2,3,4]
const [num0 , num3, num4] = array
console.log(num2) // 0
console.log(num4) // 1
console.log(num5) // 2
객체에서는 변수의 이름이 중요했지만, 배열에서는 변수이름과 관련 없이 배열의 순서대로 들어간다.
따라서 각 인덱스에 맞게 변수에 값을 담으려면 다음과 같이 작성한다.
const [ , num1 , , num3, num4] = array
// num1 = 1 , num3 = 3, num4 = 4
이제 실습으로 유튜버라는 객체를 만들고, 각 유튜버의 채널에 접속하면 데이터 값들을 출력해보도록 하겠다.
// 객체 생성
let youtuber1 = {
channel : "1st"
subscribers : "1천명"
videoes : "10개"
}
let youtuber2 = {
channel : "2nd"
subscribers : "2천명"
videoes : "20개"
}
let youtuber3 = {
channel : "3rd"
subscribers : "3천명"
videoes : "30개"
}
//
app.get('/:name', function(req, res){
const {name} = req.params
// 내가 알고 있는 유튜버들은, 해당 데이터 값을 반환시켜준다.
if (name==="1st"){
res.json(youtuber1)
}
else if (name==="2nd"){
res.json(youtuber2)
}
else if (name === "3rd"){
res.json(youtuber3)
}
// 예외 : 내가 모르는 유튜버 채널이름이 들어왔을 때( 4th, 5th... ) 는 예외처리를 해준다.
else {
res.send('잘못된 접근입니다.')
}
})
map이라는 자료형은 object 자료형과 비슷하게 key, value 값을 가진다.
하지만 값을 넣는 방법과, 출력시 결과가 다르게 나타난다.
값을 넣을 땐, 변수명.set(key,value) 를 이용하고,
value를 얻을 땐, 변수명.get(key) 를 사용한다.
let myMap = new Map()
myMap.set(1, "첫번째값")
myMap.set(2, "두번째값")
myMap.set(3, "세번째값")
console.log(myMap) // Map(3) { 1 => '첫번째값', 2 => '두번째값', 3 => '세번째값' }
console.log(myMap.get(1)) // "첫번째값"
console.log(myMap.get(2)) // "두번째값"
console.log(myMap.get(3)) // "세번째값"
그렇다면 위의 실습으로
url로 1을 받으면 첫번째값,
url로 2을 받으면 두번째값,
url로 3을 받으면 세번째값,
을 출력해도록 해보겠다.
let db = new Map()
const express = require("express")
const app = express()
db.set(1, "첫번째값")
db.set(2, "두번째값")
db.set(3, "세번째값")
app.get('/:num' , function (req, res){
let {num} = req.params
num = parseInt(num)
if (db.get(num)){ // db에 해당하는 객체가 없으면 undefined 반환되어 else문 실행
res.json({
num : num ,
val : db.get(num)
})
}
else {
res.json({message : "없는 상품입니다."})
}
})
app.listen(3000)
작성한 뒤, http://localhost:3000/1 URL을 입력하여 각 map 객체에 해당하는 데이터값을 출력하는 것을 알 수 있다.