Svelte TIL 04
참고
@html
<!-- [코드 4-1] App.svelte-->
<script>
let h1 = '<h1>hello world</h1>';
</script>
{@html h1}
@html 키워드를 통해 문자열 내부를 html으로 평가하여 보여준다. xss의 위험이 있으므로 문자열을 적절히 필터링하는 전처리가 필요하다.
@debug
<!-- [코드 4-2] App.svelte-->
<script>
let cnt = 0;
</script>
{@debug cnt}
<button on:click={ () => cnt++ }>up</button>
cnt값이 바뀔 때 마다 cnt의 값을 console.log()
없이도 개발자도구에 출력해준다. 개발자도구가 닫혀있다면 console탭에 로그가 쌓이기만 한다. 만약 개발자 도구가 켜있다며 로그가 쌓임과 동시에 코드가 일시정지된다.
데이터의 불변성과 가변성
JS의 원시데이터(숫자, 문자열, null, symbol, undefined 등)는 Immutable하다.(불변성) 한 번 메모리에 할당되면 변경될 수 없다. 원시데이터를 값으로 갖는 변수에 새 값이 할당된다면, 새로운 번지에 데이터를 할당 한 뒤 변수가 가리키는 번지를 변경한다.
객체(Object, Array 등)는 Mutable하다.(가변성) 메모리에 할당되었더라도 변경될 수 있다.
할당과 반응성
<!-- [코드 4-3] App.svelte-->
<script>
let arr = ['x', 'y'];
let obj = {
a : 123,
b : [1, 2],
};
function assign() {
arr.push('z');
obj.a = 456;
obj.b.push(3);
}
</script>
<button on:click={assign}>assign</button>
<h1>{arr}</h1>
<h1>{obj.a}</h1>
<h1>{obj.b}</h1>
위 코드에서 버튼을 누르면 arr는 값이 그대로이고, obj.a와 obj.b의 값만 변화한다.
arr.push('z')
는 대입연산이 없었으므로 반응성을 갖지 않는다. 아래 [코드 4-4]에서 해결해보자.obj.a = 456
은 새 값이 대입되었으므로 반응성을 갖는다.obj.b.push(3)
은 arr와 사실상 동일한 코드이지만, 이상하게도 반응성을 가졌다. [코드 4-5]에서 다시 살펴보자.
<!-- [코드 4-4] App.svelte-->
<script>
let arr = ['x', 'y'];
function assign_1() {
arr = [...arr, 'z'];
}
function assign_2() {
arr.push('z');
arr = arr;
}
</script>
<button on:click={assign_1}>assign_1</button>
<button on:click={assign_2}>assign_2</button>
<h1>{arr}</h1>
arr에 하여금 반응성을 갖도록 하는 방법 두 가지를 작성했다. 둘 모두 대입연산을 포함한다는 공통점을 갖고있다.
<!-- [코드 4-5] App.svelte-->
<script>
let obj = {
a : 123,
b : [1, 2],
};
function change_a_and_b() {
obj.a = 456;
obj.b.push(3);
}
function change_only_b() {
obj.b.push(3);
}
</script>
<button on:click={change_a_and_b}>a and b</button>
<button on:click={change_only_b}>b</button>
<h1>{obj.a}</h1>
<h1>{obj.b}</h1>
문제의 obj.b.push(3)
을 살펴보자. change_a_and_b
를 실행하면 obj.b
가 반응성을 갖는다. 그러나 change_only_b
를 실행하면 obj.b
가 반응성을 갖지 못한다.
TIL 03 포스트에서 살펴본 바와 같이, 대입과 동시에 Re-render가 일어나는 것이 아니라 일정 단위로 Re-render가 일어난다. change_a_and_b()
를 통해obj.a = 456
이 실행되면 svelte는 obj.a
뿐 아니라 obj
전체를 갱신한다. 그 시점에서는 obj.a
와 obj.b
모두 값이 바뀌었으므로 화면으로 볼 때에는 둘 모두 Re-render된다. obj.b
는 영문도 모른채 obj.a
덕분에 반응성을 갖게 된 것이다.
반응성 구문
개요
<!-- [코드 4-6] App.svelte-->
<script>
let text = 'a';
let doubleText;
$ : {
doubleText = text + text;
console.log(doubleText.length, doubleText);
}
</script>
<h1 on:click={()=>{text=text+'a';}}>{text.length}{text}</h1>
$라는 이름의 label구문에 포함된 어떤 변수가 반응성을 가질 때, 해당 label구문을 실행한다.
반응성 구문의 trigger가 되는 변수가 label구문 안으로 몇depth를 들어가는지는(어떤 scope를 갖는지) 상관없다.
일반형
let doubleText;
$ : {
doubleText = text + text;
}
축약형
$ : doubleText = text + text;
블록없이 콜론 :
뒤에 바로 변수명을 명시하면, 별도 선언없이 doubleText
변수를 만든다. doubleText
는 text
의 반응성에 뒤이어 반응성을 갖는다.
함수실행
$: text, (()=>{console.log(text);})
조건문/반복문
$: if(text==='aaaa'){console.log(text);}
$: for(let i=0; i<10; i++){
text;
console.log(i);
}
Author And Source
이 문제에 관하여(Svelte TIL 04), 우리는 이곳에서 더 많은 자료를 발견하고 링크를 클릭하여 보았다 https://velog.io/@yiwonjin/Svelte-TIL-04저자 귀속: 원작자 정보가 원작자 URL에 포함되어 있으며 저작권은 원작자 소유입니다.
우수한 개발자 콘텐츠 발견에 전념 (Collection and Share based on the CC Protocol.)