vue 의 양 방향 연결 로 todo-list 의 예제 코드 를 간단하게 실현 합 니 다.

10055 단어 vuetodolist
머리말
최근 에 vue 프레임 워 크 의 기본 원 리 를 배우 고 일부 기술 블 로그 와 vue 소스 코드 에 대한 간단 한 실현 을 보 았 으 며 데이터 에이전트,데이터 납치,템 플 릿 분석,변이 배열 방법,양 방향 연결 에 대해 더욱 깊이 이해 했다.그래서 자신 이 배 운 지식 을 실천 하고 vue 의 기본 원리 로 간단 한 todo-list 를 실현 하여 깊이 있 고 복잡 한 대상 에 대한 양 방향 연결 과 배열 에 대한 감청 을 완성 하여 vue 의 기본 원리 에 대한 인상 을 강화 했다.
github 주소:todo-list
학습 링크
앞줄 은 다음 과 같은 글 에 감 사 드 립 니 다.vue 의 기본 원 리 를 이해 하 는 데 큰 도움 이 됩 니 다!
vue 실현 원 리 를 분석 하고 스스로 mvvm 를 실현 하 다. by DMQ 
vue 초기 소스 코드 에 대한 이해 by양소 봉
실현 효과

데이터 에이전트
1.데이터 에이전트 소개
정상 적 인 상황 에서 우 리 는 모두 데 이 터 를 data 안에 쓸 것 이다.아래 와 같다.

var vm = new Vue({
  el: '#app',
  data: {
    title: 'hello world'
  }
  methods: {
    changeTitle: function () {
      this.title = 'hello vue'
    }
  }
})
console.log(vm.title) // 'hello world' or 'hello vue'
데이터 에이전트 가 없 으 면 데이터 에 있 는 title 을 수정 해 야 합 니 다.methods 에 있 는 changeTitle 은 이렇게 만 수정 할 수 있 습 니 다this.data.title = 'hello vue'.아래 console 도console.log(vm.data.title),데이터 에이전트 로 만 변경 할 수 있 습 니 다.
2.실현 원리
data 의 속성 을 옮 겨 다 니 며 모든 속성 을 object.defineProperty()를 통 해 getter 와 setter 를 설정 하고 data 의 모든 속성 을 data 와 같은 등급 의 대상 에 복사 합 니 다.
(위의 예제 코드 에 대응)
 
이 곳 의 getter 를 터치 하면 data 에 대응 하 는 속성 을 가 진 getter 를 터치 합 니 다.이 곳 의 setter 를 터치 하면 data 에 대응 하 는 속성 을 가 진 setter 를 터치 하여 대 리 를 실현 합 니 다.구현 코드 는 다음 과 같 습 니 다:

var self = this;  // this vue  ,  vm
Object.keys(this.data).forEach(function(key) {
  Object.defineProperty(this, key, {  // this.title,  vm.title
    enumerable: false,
    configurable: true,
    get: function getter () {
      return self.data[key];  //    data[key] getter
    },
    set: function setter (newVal) {
      self.data[key] = newVal; //    data[key] setter
    }
  });
}
object.defineProperty 에 익숙 하지 않 은 친구 들 은MDN 문서(링크)에서 배 울 수 있 습 니 다.
양 방향 바 인 딩
  • 데이터 변동--->보기 업데이트
  • 보기 업데이트(input,textarea)-->데이터 변동
  • --> 이 방향의 연결 은 비교적 간단 하 다.주로 사건 감청 을 통 해 데 이 터 를 바꾼다.예 를 들 어 input 은 input 사건 을 감청 할 수 있 고 input 사건 이 발생 하면 data 를 바꾼다.다음은 ---> 이 방향의 연결 을 이해 해 보 겠 습 니 다.
    1.데이터 납치
    데이터 변동 을 어떻게 실현 하고 바 인 딩 데이터 에 대응 하 는 보 기 를 업데이트 하 는 지 스스로 생각해 보 자.
    정 답 은 object.defineProperty 입 니 다.object.defineProperty 를 통 해 this.data 의 모든 속성 을 설정 하고 각 속성의 setter 에서 해당 하 는 리 셋 함 수 를 알려 줍 니 다.이곳 의 리 셋 함 수 는 dom 보기 로 다시 보 여 주 는 함수,$watch 로 추 가 된 리 셋 함수 등 을 포함 합 니 다.그러면 우 리 는 object.defineProperty 를 통 해 데 이 터 를 납치 합 니 다.우리 가 데 이 터 를 다시 할당 할 때this.title = 'hello vue'는 setter 함 수 를 촉발 하여 dom 보기 가 다시 렌 더 링 하 는 함 수 를 촉발 하여 데이터 변동 을 실현 하고 보기 업데이트 에 대응 합 니 다.
    2.게시-구독 모드
    그러면 문제 가 생 겼 습 니 다.우 리 는 어떻게 setter 에서 이 데 이 터 를 연결 하 는 리 셋 함 수 를 촉발 합 니까?
    이 데 이 터 를 연결 하 는 리 셋 함수 가 하나 가 아 닌 이상 모든 리 셋 함 수 를 한 배열 에 넣 습 니 다.이 데 이 터 를 촉발 하 는 setter 는 배열 을 옮 겨 다 니 며 모든 리 셋 함 수 를 촉발 합 니 다.우 리 는 이 리 셋 함 수 를 구독 자 라 고 부 릅 니 다.배열 은 setter 함수 의 최근 상위 역할 영역 에서 다음 인 스 턴 스 코드 와 같이 정의 하 는 것 이 좋 습 니 다.
    
    Object.keys(this.data).forEach(function(key) {
      var subs = []; //                
      Object.defineProperty(this.data, key, {  // this.data.title
        enumerable: false,
        configurable: true,
        get: function getter () {
          console.log('       ')
          return this.data[key];  //        
        },
        set: function setter (newVal) {
          if (newVal === this.data[key]) {  
            return;  //         ,    ,        
          }
          this.data[key] = newVal; //      
          
          subs.forEach(function () {
            //   subs         
          })
        }
      });
    }
    
    그러면 문제 가 또 생 겼 습 니 다.어떻게 바 인 딩 데이터 의 모든 반전 함 수 를 한 배열 안에 넣 습 니까?
    우 리 는 getter 에서 손발 을 할 수 있 습 니 다.데이터 에 접근 하면 해당 하 는 데이터 의 getter 를 촉발 할 수 있다 는 것 을 알 고 있 습 니 다.그러면 우 리 는 먼저 전역 변수 target 을 설정 할 수 있 습 니 다.만약 에 data 에 title 속성 에 구독 자(changeTitle 함수)를 추가 하려 면 target=changeTitle 을 설정 하고 changeTitle 함 수 를 target 에 캐 시 할 수 있 습 니 다.그리고 this.title 을 방문 하여 title 의 getter 를 촉발 합 니 다.getter 에서 target 이라는 전역 변수의 값 을 subs 배열 에 추가 하고 완료 후 전역 변 수 를 target 을 null 로 설정 하여 다른 구독 자 를 추가 할 수 있 습 니 다.인 스 턴 스 코드 는 다음 과 같 습 니 다.
    
    Object.keys(this.data).forEach(function(key) {
      var subs = []; //                
      Object.defineProperty(this.data, key, {  // this.data.title
        enumerable: false,
        configurable: true,
        get: function getter () {
          console.log('       ')
          if (target) {
            subs.push(target);        
          }
          return this.data[key];  //        
        },
        set: function setter (newVal) {
          if (newVal === this.data[key]) {  
            return;  //         ,    ,        
          }
          this.data[key] = newVal; //      
          
          subs.forEach(function () {
            //   subs         
          })
        }
      });
    }
    
    위의 코드 는 이해 하기 편 하도록 모두 간소화 되 었 습 니 다.실제로 우 리 는 구독 자 를 구조 함수 watcher 로 작성 하고 구독 자 를 예화 할 때 해당 하 는 데 이 터 를 방문 하여 해당 하 는 getter 를 촉발 합 니 다.상세 한 코드 는 읽 을 수 있 습 니 다DMQ 의 자체 손 으로 MVVM 실현.
    3.템 플 릿 분석
    위의 두 단 계 를 통 해 우 리 는 데이터 가 변동 하면 바 인 딩 데이터 에 대응 하 는 구독 자 에 게 알 리 는 것 을 실 현 했 습 니 다.그 다음 에 우 리 는 특수 한 구독 자,즉 보기 업데이트 함수,거의 모든 데이터 에 대응 하 는 보기 업데이트 함 수 를 추가 하기 때문에 보기 업데이트 함 수 를 간단하게 알 아 보 겠 습 니 다.
    만약 아래 의 이 코드 가 있다 면,우 리 는 어떻게 그것 을 대응 하 는 html 로 해석 합 니까?
    
    <input v-model="title">
    <h1>{{title}}</h1>
    <button v-on:click="changeTitle">change title<button>
    먼저 보기 업데이트 함수 의 용 도 를 간단하게 소개 합 니 다.
    예 를 들 어 해석 명령v-model="title",v-on:click="changeTitle",그리고{{title}}을 대응 하 는 데이터 로 바 꾸 는 등.
    위의 그 문제 로 돌아 가 템 플 릿 을 어떻게 해석 합 니까?우 리 는 모든 dom 노드 를 옮 겨 다 니 면 하위 노드 를 포함 합 니 다.
  • 노드 속성 에 v-model 이 포함 되 어 있 으 면 보기 업데이트 함 수 는 input 의 value 를 title 의 값 으로 설정 합 니 다
  • 노드 가 텍스트 노드 라면 보기 업데이트 함 수 는 정규 표현 식 으로 괄호 안의 값'title'을 꺼 내 고 텍스트 노드 의 값 을 data[title]
  • 로 설정 합 니 다.
  • 노드 속성 에 v-on:xxxx 가 포함 되 어 있 으 면 보기 업데이트 함 수 는 정규 로 이벤트 형식 을 click 으로 가 져 온 다음 에 이 속성의 값 을 changeTitle 로 가 져 오 면 이벤트 의 리 셋 함 수 는 this.methods[changeTitle]이 고 이 어 addEventListener 로 노드 click 이 벤트 를 감청 합 니 다.
  • 보기 업데이트 함수 도 data 에 대응 하 는 속성 을 가 진 구독 자 임 을 알 아야 합 니 다.보기 업데이트 함 수 를 어떻게 터치 하 는 지 모 르 면 위의 게시-구독 모드 를 다시 한 번 볼 수 있 습 니 다.
    일부 파트너 들 은 input 노드 의 값 변 화 를 어떻게 실현 하 는 지 의문 이 있 을 수 있 습 니 다.아래 h1 노드 의 title 값 도 변화 합 니까?모든 노드 를 옮 겨 다 닌 후 노드 에 속성 v-model 이 있 으 면 addEventListener 로 input 이 벤트 를 감청 합 니 다.input 이벤트 가 발생 하면 data[title']의 값 을 바 꾸 면 title 의 setter 를 촉발 하여 모든 구독 자 에 게 알 립 니 다.
    감청 배열 변화
    각 배열 요 소 를 감시 할 수 없습니다.
    만약 에 우리 가 스스로 감청 배열 의 변 화 를 실현 한다 면 우 리 는 object.defineProperty 로 배열 의 모든 요 소 를 옮 겨 다 니 며 setter 를 설정 하 는 것 을 생각 할 수 있 습 니 다.그러나 vue 소스 코드 에는 이렇게 쓰 여 있 지 않 습 니 다.모든 배열 요소 defineProperty 에 코드 자체 의 복잡성 증가 와 코드 집행 효율 이 떨 어 지기 때 문 입 니 다.
    변이 배열 방법
    define Property 를 통 해 배열 의 모든 요 소 를 감시 할 수 없 으 므 로 배열 의 방법(push,pop,shift,unshift,splice,sort,reverse)을 다시 써 서 배열 을 바 꿀 수 있 습 니 다.
    vue 문서 에 이렇게 쓰 여 있 습 니 다:
    Vue 는 배열 의 변 이 를 관찰 하 는 방법 을 포함 하고 있 기 때문에 보기 업 데 이 트 를 촉발 합 니 다.이 방법 들 은 다음 과 같다.
  • push()
  • pop()
  • shift()
  • unshift()
  • splice()
  • sort()
  • reverse()
  • 다음은vue 초기 소스 학습 시리즈 2:한 배열 의 변 화 를 어떻게 감청 합 니까?의 인 스 턴 스 코드 입 니 다.
    
    const aryMethods = ['push', 'pop', 'shift', 'unshift', 'splice', 'sort', 'reverse'];
    const arrayAugmentations = [];
    
    aryMethods.forEach((method)=> {
    
      //      Array     
      let original = Array.prototype[method];
    
      //  push, pop            arrayAugmentations    
      //   :         
      arrayAugmentations[method] = function () {
        console.log('     !');
    
        //               
        return original.apply(this, arguments);
      };
    
    });
    
    let list = ['a', 'b', 'c'];
    //                           
    //                      push   
    list.__proto__ = arrayAugmentations;
    list.push('d'); //      ! 4
    
    //    list2           ,       
    let list2 = ['a', 'b', 'c'];
    list2.push('d'); // 4
    
    
    변이 배열 방법의 결함
    vue 문서 의 변이 배열 방법의 결함
    JavaScript 의 제한 으로 인해 Vue 는 다음 과 같은 변 경 된 배열 을 감지 할 수 없습니다.
  • 색인 을 이용 하여 항목 을 직접 설정 할 때,예 를 들 어 vm.items[indexOfItem]=new Value
  • 배열 의 길 이 를 수정 할 때,예 를 들 어 vm.items.length=new Length
  • 이 동시에 문서 에서 도 위의 두 문 제 를 어떻게 해결 하 는 지 소개 했다.
    마지막.
    이상 은 자신 이 vue 의 기본 원리 에 대한 이해 입 니 다.물론 부족 한 점 이 많 습 니 다.지적 을 환영 합 니 다.원래 자신 도 면접 에 대비 하여 vue 프레임 워 크 의 기본 원 리 를 배 웠 지만 이러한 vue 기본 원 리 를 간단하게 배 운 후에 저 는 프레임 워 크 원 리 를 깊이 공부 함으로써 자신 이 나중에 만 날 수 있 는 구 덩이 를 효과적으로 피 할 수 있다 는 것 을 깨 달 았 습 니 다.그래서 시간 이 있 으 면 나중에 프레임 워 크 의 기본 원 리 를 보 겠 습 니 다.
    이상 이 바로 본 고의 모든 내용 입 니 다.여러분 의 학습 에 도움 이 되 고 저 희 를 많이 응원 해 주 셨 으 면 좋 겠 습 니 다.

    좋은 웹페이지 즐겨찾기