Reactive Data-binding ใน VueJS

ช่วงนี้มีคนพูดถึง VueJS ค่อนข้างบ่อยเหมือนกัน วันนี้ผมจะมาพูดถึงว่า Reactive Data-binding ใน VueJS คืออะไร ??

Reactive แปลเป็นภาษาง่าย ๆ ก็คือ การโต้ตอบทันที
เช่น การคำนวณผลลัทพ์ทันทีเมื่อตัวแปรในสมการเปลี่ยน

ใน AngularJS จะมี Digest Loop เพื่อตรวจสอบว่ามีตัวแปรอะไรใน DOM เปลี่ยนบ้างหลังเกิด event เช่น กดปุ่ม ทำให้เสียเวลาเช็คเมื่อมีตัวแปรจำนวนมาก

แต่ใน VueJS ค่าใน DOM จะถูกเปลี่ยนทันทีที่มีการเปลี่ยนค่าตัวแปร ทำให้ไม่ต้องเช็คว่าตัวแปรไหนถูกเปลี่ยน

แล้วจะรู้ได้ยังไงว่าตัวแปรถูกเปลี่ยน ???

ลองดูตัวอย่างง่าย ๆ ใน JavaScript

const obj = {}
Object.defineProperty(obj, 'name', {
get () {
console.log('get name')
return this._name
},
set (value) {
console.log('set name to ' + value)
this._name = value
}
})
obj.name = 'acoshift'
console.log(obj.name)

ผลลัพท์คือ

set name to acoshift
get name
acoshift

ในทำนองเดียวกัน VueJS ใส่ Observer ไว้ใน Properties ทุกตัวใน Object เมื่อค่าในตัวแปรถูกเปลี่ยน Observer จะส่งบอกให้ Vue ไปอัพเดท DOM

เลยเป็นเหตุผลว่าทำไม VueJS ถึงเร็วกว่า AngularJS เพราะว่าไม่ต้องไปเช็คตัวแปรทุกตัว และไม่ต้องใช้ $scope.$apply() เพื่อรัน digest loop

ตัวอย่าง การใช้ VueJS

<!doctype html>
<script src="https://cdnjs.cloudflare.com/ajax/libs/vue/2.0.0-rc.5/vue.min.js"></script>
<app>
<h1>Hello, {{ name }}</h1>
{{ input }}^2 = {{ output }}<br>
<input v-model="input">
</app>
<script>
new Vue({
data () {
return {
input: ''
}
},
computed: {
output () {
console.log('output')
return this.input * this.input
},
name () {
console.log('name')
return 'acoshift'
}
}
}).$mount('app')
</script>

จะเห็นว่า output ถูก call เมื่อตัวแปร input เปลี่ยน แต่ name จะถูก call แค่ครั้งแรกครั้งเดียว

เนื่องจาก VueJS ใช้ Observer ในการดูว่าตัวแปรไหนถูกเปลี่ยน ดังนั้นเราจึงสามารถแชร์ data ระหว่าง component/service แบบ Reactive ได้ เช่น

<!doctype html>
<script src="https://cdnjs.cloudflare.com/ajax/libs/vue/2.0.0-rc.5/vue.min.js"></script>
<app>
<div v-if="currentUser">
<h1>Hello, {{ currentUser.name }}</h1>
<button @click="signOut">Sign Out</button>
</div>
<div v-else>
<button @click="signIn">Sign In</button>
</div>
</app>
<script>
const auth = new Vue({
data () {
return {
currentUser: null
}
},
methods: {
signIn () {
this.currentUser = { name: 'acoshift' }
},
signOut () {
this.currentUser = null
}
}
})
new Vue({
computed: {
currentUser () {
return auth.currentUser
}
},
methods: {
signIn () {
auth.signIn()
},
signOut () {
auth.signOut()
}
}
}).$mount('app')
</script>

จะเห็นว่าเมื่อ currentUser ใน auth เปลี่ยน ตัวแปร currentUser ใน app จะถูกเปลี่ยนด้วย


ถ้าต้องการติดตามเรื่องราวเกี่ยวกับ Programming ของผมสามารถติดตามได้ใน Page FB https://www.facebook.com/acoshift นะครับ :3

Like what you read? Give acoshift a round of applause.

From a quick cheer to a standing ovation, clap to show how much you enjoyed this story.