Vue的列表渲染

本文介绍了Vue中v-for指令用于列表渲染的基本用法,包括遍历数组、对象、字符串及指定次数。通过示例展示了key的作用,解释了key在虚拟DOM中作为标识的重要性,并对比了使用index和唯一标识作为key的区别。同时,文章还涵盖了列表的过滤和排序功能,使用computed属性实现动态搜索和年龄排序。
摘要由CSDN通过智能技术生成

一、列表初识

v-for指令:

  1. 用于展示列表数据
  2. 语法:v-for="(item, index) in xxx" :key="yyy"
  3. 可遍历数组,对象,字符串,指定字数;其中遍历数组和对象最常用;

新建【列表渲染.html】

<!DOCTYPE html>
<html>
    <head>
        <meta charset="UTF-8" />
        <title>列表渲染</title>
        <style>
        </style>
        <!-- 引入Vue -->
        <script type="text/javascript" src="https://cdn.jsdelivr.net/npm/vue@2/dist/vue.js"></script>
    </head>
    <body>
        <!-- 准备好一个容器 -->
        <div id="root">
        <!--遍历数组-->
        <h2>遍历数组</h2>
          <ul>
              <li v-for="person in persons" :key="person.id">
                  姓名:{{person.name}} - 年龄:{{person.age}}
                </li>
          </ul>
          <hr>
          <ul>
            <li v-for="(person,index) in persons" :key="index">
                姓名:{{person.name}} - 年龄:{{person.age}}
            </li>
        </ul>
        <ul>
            <li v-for="(person,index) of persons" :key="index">
                姓名:{{person.name}} - 年龄:{{person.age}}
            </li>
        </ul>
        <hr>
        <hr>

        <!--遍历对象-->
        <h2>遍历对象</h2>
        <ul>
            <li v-for="(value,key) of car" :key="key" >
              {{key}} - {{value}} 
            </li>
        </ul>

         <!--遍历字符串-->
         <h2>遍历字符串</h2>
         <ul>
             <li v-for="(str,index) of hello" :key="index" >
               索引值:{{index}} - 字符串值:{{str}} 
             </li>
         </ul>

         <!--遍历指定次数-->
         <h2>遍历指定次数</h2>
         <ul>
             <li v-for="(num,index) of 5" :key="index" >
               索引值:{{index}} - 数值{{num}} 
             </li>
         </ul>
        </div>
        <!--阻止vue在启动时生成生产提示 -->
        <script type="text/javascript">
        Vue.config.productionTip=false
         // 创建Vue实例
         new Vue({
             el:"#root",  
             data:{
               persons:[
                   {
                       id: "001",
                       name:"张三",
                       age: 28,
                    },
                    {
                       id: "002",
                       name:"王五",
                       age: 18,
                    },
                    {
                       id: "003",
                       name:"李四",
                       age: 38,
                    }
               ],
               car:{
                   name:"奥迪A8",
                   price:"70W"
               },
               hello: "hello",

             },
             methods:{
                
             }
            
                
            
         })
        </script>
       
    </body>
</html>

key的作用和原理

1. 使用index作为key

新建文件【使用index作为key.html】
关注点:使用index作为key
注意:如果不写key,vue会默认使用index作为key。

<!DOCTYPE html>
<html>
    <head>
        <meta charset="UTF-8" />
        <title>key的原理</title>
        <style>
        </style>
        <!-- 引入Vue -->
        <script type="text/javascript" src="https://cdn.jsdelivr.net/npm/vue@2/dist/vue.js"></script>
    </head>
    <body>
        <!-- 准备好一个容器 -->
        <div id="root">
        <!--遍历数组-->
        <h2>遍历数组</h2>
        <button @click="add">添加一个人</button>
        <ul>
            <li v-for="(person,index) of persons" :key="index">
                姓名:{{person.name}} - 年龄:{{person.age}}
                <input type="text">
            </li>
        </ul>

        </div>
        <!--阻止vue在启动时生成生产提示 -->
        <script type="text/javascript">
        Vue.config.productionTip=false
         // 创建Vue实例
         new Vue({
             el:"#root",  
             data:{
               persons:[
                   {
                       id: "001",
                       name:"张三",
                       age: 28,
                    },
                    {
                       id: "002",
                       name:"王五",
                       age: 18,
                    },
                    {
                       id: "003",
                       name:"李四",
                       age: 38,
                    }
               ],
             },
             methods:{
                add(){
                    const p = {"id": "004", "name": "jane", "age":30}
                    this.persons.unshift(p)
                }
             }
            
                
            
         })
        </script>
       
    </body>
</html>

使用浏览器打开,每一个输入框都输入值后,点击按钮添加一个人,效果如下:
在这里插入图片描述

具体作用原理可看下图:
在这里插入图片描述

2. 使用id作为key

新建文件【使用id作为key.html】
关注点:使用id作为key

<!DOCTYPE html>
<html>
    <head>
        <meta charset="UTF-8" />
        <title>key的原理</title>
        <style>
        </style>
        <!-- 引入Vue -->
        <script type="text/javascript" src="https://cdn.jsdelivr.net/npm/vue@2/dist/vue.js"></script>
    </head>
    <body>
        <!-- 准备好一个容器 -->
        <div id="root">
        <!--遍历数组-->
        <h2>遍历数组</h2>
        <button @click="add">添加一个人</button>
        <ul>
            <li v-for="(person,index) of persons" :key="person.id">
                姓名:{{person.name}} - 年龄:{{person.age}}
                <input type="text">
            </li>
        </ul>

        </div>
        <!--阻止vue在启动时生成生产提示 -->
        <script type="text/javascript">
        Vue.config.productionTip=false
         // 创建Vue实例
         new Vue({
             el:"#root",  
             data:{
               persons:[
                   {
                       id: "001",
                       name:"张三",
                       age: 28,
                    },
                    {
                       id: "002",
                       name:"王五",
                       age: 18,
                    },
                    {
                       id: "003",
                       name:"李四",
                       age: 38,
                    }
               ],
             },
             methods:{
                add(){
                    const p = {"id": "004", "name": "jane", "age":30}
                    this.persons.unshift(p)
                }
             }
            
                
            
         })
        </script>
       
    </body>
</html>

使用浏览器打开,每一个输入框都输入值后,点击按钮添加一个人,效果如下:
在这里插入图片描述

具体作用原理可看下图:
在这里插入图片描述

3. 总结

  1. 虚拟DOM中key的作用

    • key是虚拟DOM对象得标识,当数据发生变化时,vue会根据【新数据】生成【新的虚拟DOM】。
    • 随后Vue进行【新虚拟DOM】与【旧虚拟DOM】的差异比较,比较规则如下。
  2. 比较规则

    • 旧的DOM中找到了与新虚拟DOM相同的key
      • 若虚拟DOM中内容没变,直接使用之前的真实DOM!
      • 若虚拟DOM中内容变了,则生成新的真实DOM,随后替换掉页面中之前的真实DOM。
    • 旧虚拟DOM未找到与新虚拟DOM相同key
      • 创建新的展示DOM,随后渲染到页面。
  3. 用index作为key可能会引发的问题

    • 若对数进行:逆向添加,逆向删除等破坏顺序操作会产生没有必要的真实DOM更新==>页面效果没有问题,但是效率低。
    • 如果结构中还包含输入类的DOM会产生错误的DOM更新==>界面有问题。
  4. 开发中如何选择key

    • 最好使用每条数据的为之一标识作为key,比如id,手机号,身份证号,学号等唯一值。
    • 如果不存在对数据的逆向添加,逆向删除等破坏顺序操作,仅用于渲染列表用于展示,使用index作为key是没有问题的。

二、列表过滤

新建【列表过滤.html】
需求:可以使用搜索关键字对人员列表的姓名进行模糊搜索
注意:当watch和computed都可以实现时,推荐使用computed。

<!DOCTYPE html>
<html>
    <head>
        <meta charset="UTF-8" />
        <title>列表过滤</title>
        <style>
        </style>
        <!-- 引入Vue -->
        <script type="text/javascript" src="https://cdn.jsdelivr.net/npm/vue@2/dist/vue.js"></script>
    </head>
    <body>
        <!-- 准备好一个容器 -->
        <div id="root">
        <h2>人员列表</h2>
        <input type="text" placeholder="请输入名字进行搜索" v-model="keyWord">
          <ul>
              <li v-for="person in filPersons" :key="person.id">
                  姓名:{{person.name}} - 年龄:{{person.age}}
                </li>
          </ul>
        </div>
        <!--阻止vue在启动时生成生产提示 -->
        <script type="text/javascript">
        Vue.config.productionTip=false
         // 创建Vue实例--watch实现
        //  new Vue({
        //      el:"#root",  
        //      data:{
        //          keyWord:"",
        //        persons:[
        //              {
            // id: "001",name:"马冬梅",age: 28,gender: "female"
            //         },
            //         {
            //            id: "002", name:"周杰伦",age: 18,gender: "male"
            //         },
            //         {
            //            id: "003",name:"温兆伦",age: 38,gender: "male"
            //         },
            //         {
            //            id: "004",name:"周冬雨",age: 38,gender: "female"
            //         }
        //        ],
        //        filPersons: []
        //      },
        //      watch:{
        //         //  keyWord(val){
        //         //      this.filPersons = this.persons.filter((person)=>{
        //         //          return persons.indexOf(val) != -1
        //         //      })
        //         //  }
        //         keyWord:{
        //             immediate:true,
        //             handler(val){
        //                 this.filPersons = this.persons.filter((person)=>{
        //                  return person.name.indexOf(val) != -1
        //              })
        //             }
        //         }
        //      }
        //  })
         // 创建Vue实例--computed实现
         new Vue({
             el:"#root",  
             data:{
                 keyWord:"",
               persons:[
                   {
                       id: "001",name:"马冬梅",age: 28,gender: "female"
                    },
                    {
                       id: "002", name:"周杰伦",age: 18,gender: "male"
                    },
                    {
                       id: "003",name:"温兆伦",age: 38,gender: "male"
                    },
                    {
                       id: "004",name:"周冬雨",age: 38,gender: "female"
                    }
               ],
             }, 
             computed:{
                 filPersons(){
                     return this.persons.filter((person)=>{
                         return person.name.indexOf(this.keyWord) !== -1
                     })
                 }
             }
         })
        </script>
       
    </body>
</html>

三、列表排序

新建【列表排序.html】

<!DOCTYPE html>
<html>
    <head>
        <meta charset="UTF-8" />
        <title>列表排序</title>
        <style>
        </style>
        <!-- 引入Vue -->
        <script type="text/javascript" src="https://cdn.jsdelivr.net/npm/vue@2/dist/vue.js"></script>
    </head>
    <body>
        <!-- 准备好一个容器 -->
        <div id="root">
        <h2>人员列表</h2>
        <input type="text" placeholder="请输入名字进行搜索" v-model="keyWord"><br>
        <br>
        <button @click="sortType=2">年龄升序</button>
        <button @click="sortType=1">年龄降序</button>
        <button @click="sortType=0">原顺序</button>
          <ul>
              <li v-for="person in filPersons" :key="person.id">
                  姓名:{{person.name}} - 年龄:{{person.age}}
                </li>
          </ul>
        </div>
        <!--阻止vue在启动时生成生产提示 -->
        <script type="text/javascript">
        Vue.config.productionTip=false
         // 创建Vue实例--computed实现
         new Vue({
             el:"#root",  
             data:{
                 keyWord:"",
                 sortType: 0, // 0原顺序,1 降序 2升序
               persons:[
                   {
                       id: "001",name:"马冬梅",age: 28,gender: "female"
                    },
                    {
                       id: "002", name:"周杰伦",age: 18,gender: "male"
                    },
                    {
                       id: "003",name:"温兆伦",age: 38,gender: "male"
                    },
                    {
                       id: "004",name:"周冬雨",age: 8,gender: "female"
                    }
               ],
             }, 
             computed:{
                 filPersons(){
                     const arr = this.persons.filter((person)=>{
                         return person.name.indexOf(this.keyWord) !== -1
                     })
                     // 判断一下是否需要排序
                     if(this.sortType){
                         arr.sort((person1, person2)=>{
                             // 函数体
                             return this.sortType === 1 ? person2.age - person1.age : person1.age -person2.age
                         })
                     }
                     return arr
                 }
             }
         })
        </script>
       
    </body>
</html>
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值