Vue练习:简单学生信息管理(增删改)

Vue练习:简单学生信息管理

1. 第一版

1.1展示效果

在这里插入图片描述

1.2 代码

App.Vue

<template>
  <div id="app">
    <div>
      <span>姓名:</span>
      <input type="text" v-model.trim="user.name"/>
    </div>
    <div>
      <span>年龄:</span>
      <input type="number" v-model="user.age"/>
    </div>
    <div>
      <span>性别:</span>
      <select v-model="user.sex">
        <option value=""></option>
        <option value=""></option>
      </select>
      <button @click="addOrEditFn">添加/修改</button>
    </div>
    <div v-show="arr.length > 0">
      <table
        border="1"
        cellpadding="10"
        cellspacing="0"
      >
        <tr>
          <th>序号</th>
          <th>姓名</th>
          <th>年龄</th>
          <th>性别</th>
          <th>操作</th>
        </tr>
        <tr v-for="(obj, index) in arr" :key="index">
          <td>{{index + 1}}</td>
          <td>{{obj.name}}</td>
          <td>{{obj.age}}</td>
          <td>{{obj.sex}}</td>
          <td>
            <button @click="delFn(index)">删除</button>
            <button @click="editFn(obj, index)">编辑</button>
          </td>
        </tr>
      </table>
    </div>
  </div>
</template>
<script>

export default {
  name: 'App',
  data(){
    return {
      //用来判断按钮执行的功能是添加(editIndex=-1)还是修改(editIndex!=-1)
      editIndex: -1,
      //表单绑定对象
      user: {name:'', age: 0, sex: ''},
      //数据源
      arr: [
        {name: 'Tom', age: 19, sex: '男'},
        {name: 'Jerry', age: 18, sex: '女'}
      ]
    }
  },
  methods: {
    addOrEditFn(){  //添加或修改方法
      if(this.editIndex === -1){
        //这里不能直接添加this.user,例如:this.arr.push(this.user),会报错,不信你试试
        this.arr.push({...this.user});
      }else{  //编辑
        this.$set(this.arr, this.editIndex, {...this.user})
        this.editIndex = -1;
      }
      this.user = {name: '', age: 0, sex: ''}
    },  
    editFn(obj, index){
      //这里也不能写this.user = obj
      this.user = {...obj};
      this.editIndex = index; //正在编辑的索引
    },
    delFn(index){
      this.arr.splice(index, 1);
    }
  }
}
</script>

2. 第二版

第二版使用了props属性,进行了组件间的通信;以及sessionStorage用来存储数据,防止刷新网页数据消失。

2.1 展示效果

在这里插入图片描述

2.2代码

Top.Vue

<template>
  <div>
    <div>
      <span>姓名:</span>
      <input type="text" v-model.trim="name"/>
    </div>
    <div>
      <span>年龄:</span>
      <input type="number" v-model.number="age"/>
    </div>
    <div>
      <span>性别:</span>
      <select v-model="sex">
        <option value=""></option>
        <option value=""></option>
      </select>
      <button @click="add">添加</button>
    </div>
  </div>
</template>

<script>
import {nanoid} from 'nanoid'

export default {
    name: 'Top',
    props: ['addStu'],
    data(){
      return {
        name: '',
        age: 0,
        sex: ''
      }
    },
    methods: {
      add(){
        const stuObj = {id: nanoid(), name: this.name, age: this.age, sex: this.sex, isEdit: false};
        this.addStu(stuObj);
        //没有操作DOM元素,直接操作的数据
        this.name = '';
        this.age = 0;
        this.sex = '';
      }
    }
};
</script>

<style>
  div{
    margin: 10px 20px;
  }
  button{
    margin-left: 20px;
  }
</style>

Bottom.Vue

<template>
  <div>
    <table border="1" cellpadding="10" cellspacing="0">
      <tr>
        <th>序号</th>
        <th>姓名</th>
        <th>年龄</th>
        <th>性别</th>
        <th>操作</th>
      </tr>
      <tr v-for="stu in stuList" :key="stu.id">
        <td>
          <span>{{stu.id}}</span>
        </td>
        <td>
          <input type="text" v-model="stu.name" v-show="stu.isEdit">
          <span v-show="!stu.isEdit">{{stu.name}}</span>
        </td>
        <td>
          <input type="number" v-model.number="stu.age" v-show="stu.isEdit">
          <span v-show="!stu.isEdit">{{stu.age}}</span>
        </td>
        <td>
          <select v-model="stu.sex" v-show="stu.isEdit">
            <option value=""></option>
            <option value=""></option>
          </select>
          <span v-show="!stu.isEdit">{{stu.sex}}</span>
        </td>
        <td>
          <button @click="del(stu.id)">删除</button>
          <button @click="edit(stu)" ref="btnEdit">编辑</button>
        </td>
      </tr> 
    </table>
  </div>
</template>

<script>

export default {
    name: 'Bottom',
    props: ['stuList', 'delStu', 'editStuInfo'],
    methods: {
      del(id){
        this.delStu(id);
      },
      edit(stu){
        event.target.innerHTML = stu.isEdit ? '编辑' : '保存';
        this.editStuInfo(stu.id);
      }
    }
};
</script>

<style scoped>
  button{
    margin: 5px 5px;
  }
</style>

App.Vue

<template>
  <div id="app">
    <h1>学生信息管理系统</h1>
    <Top :addStu="addStu"/>
    <Bottom :stuList="stuList" :delStu="delStu" :editStuInfo="editStuInfo"/>
  </div>
</template>
<script>
import Top from './components/Top'
import Bottom from './components/Bottom'

export default {
  name: 'App',
  components: {Top, Bottom},
  data(){
    return {
      stuList: JSON.parse(sessionStorage.getItem('stuList')) || []
    } 
  },
  watch: {
    stuList: {
      deep: true, //开启深度监视,否则无法修改sessionStorage中的数据
      handler(value){
        sessionStorage.setItem('stuList', JSON.stringify(value));
      }
    }
  },
  methods: {
    //传递给top组件,用来添加学生信息
    addStu(stuObj){
      this.stuList.unshift(stuObj);
    },
    delStu(stuId){
      this.stuList = this.stuList.filter(stu => {
        return stu.id != stuId;
      })
    },
    editStuInfo(stuId){
      this.stuList.forEach((stu) => {
        if(stu.id === stuId){
          stu.isEdit = !stu.isEdit;
        }
      })
    }
  }
}
</script>

2.3 知识点记录

2.3.1 props属性
  1. 功能:让组件接收外部传过来的数据,也可以接收外部组件传递过来的函数

  2. 传递数据和接收数据:
    传递数据:
    <Demo name='xxx'/>
    <Demo :obj='obj'/>
    接收数据:
    第一种方式(只接收):props:['name']

    第二种方式(限制类型):props:{name:String}

    第三种方式(限制类型、限制必要性、指定默认值):

props:{
	name:{
	type:String, //类型
	required:true, //必要性
	default:'老王' //默认值
	}
}

注意:props是只读的,Vue底层会监测你对props的修改,如果进行了修改,就会发出警告,若业务需求确实需要修改,那么请复制props的内容到data中一份,然后去修改data中的数据。
3. props适用于
(1)父组件 => 子组件 通信
(2)子组件 => 父组件 通信(要求父组件给子组件传递一个函数)

2.3.2 sessionStorage
  1. sessionStorage存储的内容会随着浏览器窗口关闭而消失。
  2. 相关API:
  • sessionStorage.setItem('key', 'value');
    该方法接受一个键和值作为参数,会把键值对添加到存储中,如果键名存在,则更新其对应的值。
  • sessionStorage.getItem('person');
    该方法接受一个键名作为参数,返回键名对应的值。
  • sessionStorage.removeItem('key');
    该方法接受一个键名作为参数,并把该键名从存储中删除。
  • sessionStorage.clear();
    该方法会清空存储中的所有数据。

3. 第三版

第三版使用了组件自定义事件功能进行了组件间的通信

3.1 代码

App.vue

<template>
  <div id="app">
    <h1>学生信息管理系统</h1>
    <Top v-on:addStu="addStu"/>
    <!-- 自定义事件 -->
    <Bottom :stuList="stuList" v-on:delStu="delStu" v-on:editStuInfo="editStuInfo"/>
  </div>
</template>
<script>
import Top from './components/Top'
import Bottom from './components/Bottom'

export default {
  name: 'App',
  components: {Top, Bottom},
  data(){
    return {
      stuList: JSON.parse(sessionStorage.getItem('stuList')) || []
    } 
  },
  watch: {
    stuList: {
      deep: true, //开启深度监视,否则无法修改sessionStorage中的数据
      handler(value){
        sessionStorage.setItem('stuList', JSON.stringify(value));
      }
    }
  },
  methods: {
    //传递给top组件,用来添加学生信息
    addStu(stuObj){
      console.log('自定义事件addStu被调用了');
      this.stuList.unshift(stuObj);
    },
    delStu(stuId){
      console.log('自定义事件delStu被触发了');
      this.stuList = this.stuList.filter(stu => {
        return stu.id != stuId;
      })
    },
    editStuInfo(stuId){
      console.log('自定义事件editStuInfo被触发了');
      this.stuList.forEach((stu) => {
        if(stu.id === stuId){
          stu.isEdit = !stu.isEdit;
        }
      })
    }
  }
}
</script>

Top.vue

<template>
  <div>
    <div>
      <span>姓名:</span>
      <input type="text" v-model.trim="name"/>
    </div>
    <div>
      <span>年龄:</span>
      <input type="number" v-model.number="age"/>
    </div>
    <div>
      <span>性别:</span>
      <select v-model="sex">
        <option value=""></option>
        <option value=""></option>
      </select>
      <button @click="add">添加</button>
    </div>
  </div>
</template>

<script>
import {nanoid} from 'nanoid'

export default {
    name: 'Top',
    data(){
      return {
        name: '',
        age: 0,
        sex: ''
      }
    },
    methods: {
      add(){
        const stuObj = {id: nanoid(), name: this.name, age: this.age, sex: this.sex, isEdit: false};
        this.$emit('addStu', stuObj);
        //没有操作DOM元素,直接操作的数据
        this.name = '';
        this.age = 0;
        this.sex = '';
      }
    }
};
</script>

<style>
  div{
    margin: 10px 20px;
  }
  button{
    margin-left: 20px;
  }
</style>

Bottom.vue

<template>
  <div>
    <table border="1" cellpadding="10" cellspacing="0">
      <tr>
        <th>序号</th>
        <th>姓名</th>
        <th>年龄</th>
        <th>性别</th>
        <th>操作</th>
      </tr>
      <tr v-for="stu in stuList" :key="stu.id">
        <td>
          <span>{{stu.id}}</span>
        </td>
        <td>
          <input type="text" v-model="stu.name" v-show="stu.isEdit">
          <span v-show="!stu.isEdit">{{stu.name}}</span>
        </td>
        <td>
          <input type="number" v-model.number="stu.age" v-show="stu.isEdit">
          <span v-show="!stu.isEdit">{{stu.age}}</span>
        </td>
        <td>
          <select v-model="stu.sex" v-show="stu.isEdit">
            <option value=""></option>
            <option value=""></option>
          </select>
          <span v-show="!stu.isEdit">{{stu.sex}}</span>
        </td>
        <td>
          <button @click="del(stu.id)">删除</button>
          <button @click="edit(stu)" ref="btnEdit">编辑</button>
        </td>
      </tr> 
    </table>
  </div>
</template>

<script>

export default {
    name: 'Bottom',
    props: ['stuList'],
    methods: {
      del(id){
        this.$emit('delStu', id)
      },
      edit(stu){
        event.target.innerHTML = stu.isEdit ? '编辑' : '保存';
        this.$emit('editStuInfo', stu.id);
        // this.editStuInfo(stu.id);
      }
    }
};
</script>

<style scoped>
  button{
    margin: 5px 5px;
  }
</style>

4. 参考链接

1. Vue练习合集

2. 尚硅谷老师的Vue教程,这个老师教的老好了

  • 17
    点赞
  • 91
    收藏
    觉得还不错? 一键收藏
  • 2
    评论
以下是一个简单学生信息管理系统的 Vue 练习示例: 1. 在 HTML 中定义一个表格,用于展示学生信息。 ```html <table> <thead> <tr> <th>姓名</th> <th>年龄</th> <th>性别</th> <th>成绩</th> </tr> </thead> <tbody> <tr v-for="(student, index) in students" :key="index"> <td>{{ student.name }}</td> <td>{{ student.age }}</td> <td>{{ student.gender }}</td> <td>{{ student.score }}</td> </tr> </tbody> </table> ``` 2. 在 Vue 实例中定义学生信息数据和相关操作方法。 ```js new Vue({ el: '#app', data: { students: [ { name: '张三', age: 18, gender: '男', score: 90 }, { name: '李四', age: 19, gender: '女', score: 85 }, { name: '王五', age: 20, gender: '男', score: 92 }, { name: '赵六', age: 21, gender: '女', score: 88 } ], newStudent: { name: '', age: '', gender: '', score: '' } }, methods: { addStudent: function () { this.students.push(this.newStudent); this.newStudent = { name: '', age: '', gender: '', score: '' }; }, deleteStudent: function (index) { this.students.splice(index, 1); } } }) ``` 3. 在 HTML添加表单和按钮,用于添加删除学生信息。 ```html <div id="app"> <table> <!-- 表格内容同上 --> </table> <form> <label>姓名:</label> <input type="text" v-model="newStudent.name"><br> <label>年龄:</label> <input type="number" v-model="newStudent.age"><br> <label>性别:</label> <select v-model="newStudent.gender"> <option value="男">男</option> <option value="女">女</option> </select><br> <label>成绩:</label> <input type="number" v-model="newStudent.score"><br> <button type="button" @click="addStudent">添加</button> </form> <button v-for="(student, index) in students" :key="index" @click="deleteStudent(index)">删除 {{ student.name }}</button> </div> ``` 这样,一个简单学生信息管理系统就完成了,你可以在浏览器中查看它的效果。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值