day1

1.什么是后台管理系统项目?

注意:前端领域当中,开发后台管理系统项目,并非是java、php等后台语言项目。

在前面课程当中,我们已经开发了一个项目【尚品汇电商平台项目】,这个项目主要针对的是用户(游客),可以让用户在平台当中购买产品。
但是你需要想明白一件事情,用户购买产品信息从何而来呀?

比如:前台项目当中的数据来源于卖家(公司),但是需要注意的时候,卖家它不会数据库操作。对于卖家而言,需要把产品的信息上传于服务器,写入数据库。
卖家并非程序员,不会数据库操作(增删改查)。导致卖家,找了一个程序员,开发一个产品,可以让我进行可视化操作数据库(增伤改查)

卖家(公司):组成,老板、员工。
老板:开发这个项目,对于老板而言,什么都可以操作。【产品的上架、产品的下架、查看员工的个人业绩、其他等等】
员工:可能就是查看个人业绩

后台管理系统:可以让用户通过一个可视化工具,可以实现对于数据库进行增删改查的操作。
而且需要注意,根据不同的角色(老板、员工),看到的、操作内容是不同的。

对于后台管理系统项目,一般而言,是不需要注册的。

2.模板介绍

简洁版: https://github.com/PanJiaChen/vue-admin-template 我们用这个
加强版: https://github.com/PanJiaChen/vue-element-admin

3.文件夹介绍

build

​ ------ index.js webpack配置文件【很少修改这个文件】

mock

​ ------ mock数据文件夹 【模拟一些假数据mockjs实现】,本案例使用真实数据

node_modules

​ ------ 项目依赖

public

​ ------ 静态资源,打包时不会编译这个文件夹

src------ 程序员源代码

api------ 接口请求相关

assets------ 静态资源,打包时不会编译

components ------ 一般放置非路由组件或者全局组件

icons ------ 放置了一些svg矢量图

layout ------ 放置一些组件与混入,后续组件都是在layout组件中

router ------ 路由相关

store------ vuex

style------ 样式相关

utils ------ 封装一些需要的方法比如request.js axios二次封装,以及token的存储和移出操作

views------ 放置路由组件

App.vue:根组件
main.js:入口文件
permission.js:与导航守卫先关、
settings:项目配置项文件
.env.development
.env.producation

4.登录功能

1.接口

因为我们使用的是真实接口需要替换原模板的接口

接口地址:http://39.98.123.211:8170/swagger-ui.html#/

这里将其他接口一起进行了替换

//引入axios(axios进行了二次封装)
import request from '@/utils/request'//对外暴露的登录接口函数
export function login(data) {return request({url: '/admin/acl/index/login',method: 'post',data})
}
//对外暴露的用户信息接口函数
export function getInfo(token) {return request({url: '/admin/acl/index/info',method: 'get',params: { token }})
}
//对外暴露的退出登录接口函数
export function logout() {return request({url: '/admin/acl/index/logout',method: 'post'})
}

修改axios的二次封装,真实接口成功的code=200,我们真实接口需要携带token字段,而不是提供的X-Token

service.interceptors.request.use(config => {// do something before request is sentif (store.getters.token) {// let each request carry token// ['X-Token'] is a custom headers key// please modify it according to the actual situation// config.headers['X-Token'] = getToken()config.headers['token'] = getToken()//修改后}return config},error => {// do something with request errorconsole.log(error) // for debugreturn Promise.reject(error)}
)
 if (res.code !== 20000 && res.code != 200) {Message({message: res.message || 'Error',type: 'error',duration: 5 * 1000})

因为使用了真实接口所以需要在vue.config.js配置代理跨域

devServer: {port: port,open: true,overlay: {warnings: false,errors: true},//配置代理跨域proxy: {'/dev-api': {target: 'http://39.98.123.211:8170',pathRewrite: { '^/dev-api': '' },},},},

2.源码分析

组件内

handleLogin() {//验证表单元素是否符合规则this.$refs.loginForm.validate((valid) => {if (valid) {//按钮的loading效果this.loading = true//派发一个action:user/login,带着用户名和密码this.$store.dispatch('user/login', this.loginForm)//登录成功.then(() => {//路由跳转this.$router.push({ path: this.redirect || '/' })//loading结束this.loading = false}).catch(() => {this.loading = false})} else {console.log('error submit!!')return false}})},

vuex仓库中

actions,由于之前没有async和await,模板使用的.then与.catch

 login({ commit }, userInfo) {//解构用户名与密码const { username, password } = userInforeturn new Promise((resolve, reject) => {//向服务器请求数据login({ username: username.trim(), password: password })//请求成功.then(response => {// console.log(response);//将response解构赋值给dataconst { data } = response//派发mutations业务commit('SET_TOKEN', data.token)//本地保存tokensetToken(data.token)resolve()}).catch(error => {reject(error)})})},

修改为async和await

async login({ commit }, userInfo) {//解构用户名与密码const { username, password } = userInfolet result = await login({ username: username.trim(), password: password })if (result.code == 20000) {commit('SET_TOKEN', result.data.token)setToken(result.data.token)return 'ok'} else {return Promise.reject(new Error('faile'))}},

剩余工作就是将英文文本替换成中文,较为简单不做演示,表单验证放在后面做

登录页最终结果

退出登录

由于api在上面已经做了修改,所以这里只是修改文本不做演示,退出登录组件名为Navbar

5.创建路由

1.路由目录

首页(一级路由)

权限管理(一级)

商品管理(一级)

---------品牌管理(二级)

---------平台属性管理(二级)

---------Spu管理(二级)

---------Sku管理(二级)

2.创建路由

我们的一级路由都是在Layout这个骨架下搭建的,所以一级路由的component都写Layout

 {path: '/',component: Layout,//重定向至dashboard组件,即首页redirect: '/dashboard',children: [{path: 'dashboard',name: 'Dashboard',component: () => import('@/views/dashboard/index'),meta: { title: '首页', icon: 'dashboard' }}]},{path: '/product',component: Layout,name: 'Product',meta: { title: '商品管理', icon: 'el-icon-goods' },children: [{path: '/tradeMark',name: 'TradeMark',component: () => import('@/views/product/tradeMark'),meta: { title: '品牌管理' }},{path: '/attr',name: 'Attr',component: () => import('@/views/product/Attr'),meta: { title: '平台属性管理' }},{path: '/spu',name: 'Spu',component: () => import('@/views/product/Spu'),meta: { title: 'Spu管理' }},{path: '/sku',name: 'Sku',component: () => import('@/views/product/Sku'),meta: { title: 'Sku管理' }},]},

meta中的title为菜单栏以及面包屑显示的名字

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-jKbvRwv9-1663551760268)(C:\Users\15363\AppData\Roaming\Typora\typora-user-images\image-20220916091415769.png)]

6.商品管理

这里主要是利用element-UI制作静态页面,模板的element-UI默认英文版

// set ElementUI lang to EN
// Vue.use(ElementUI, { locale })
// 如果想要中文版 element-ui,按如下方式声明
Vue.use(ElementUI)

1.品牌管理

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-piNMFlod-1663551760269)(D:\桌面\屏幕截图 2022-09-16 092103.png)]

1.添加按钮

<el-button type="primary" icon="el-icon-plus" style="margin-bottom: 10px">添加</el-button>

2.添加table表格—显示的标题要居中—且序号的占比要小

el-table属性:

data:表格组件将来需要展示的数据【数组类型】

border:是给表格带上边框

el-table-column属性:

label:显示的标题

width:对应列的宽度

align:对齐方式

<el-table :data="data" style="width: 100%" border="true"><el-table-column prop="prop" label="序号" width="80px" align="center"></el-table-column><el-table-column prop="prop" label="品牌名称" width="width"></el-table-column><el-table-column prop="prop" label="品牌logo" width="width"></el-table-column><el-table-column prop="prop" label="操作" width="width"></el-table-column></el-table>

3.分页器----要居中

 <!-- current-page:当前页数page-sizes:每页显示个数选择器page-size:每页显示条目个数total:总条目数pager-count:页码按钮的数量,当总页数超过该值时会折叠layout:实现分页器布局--><el-paginationclass="pagination":current-page="6":total="100":page-size="3":pager-count="7":page-sizes="[3, 5, 10]"@size-change="handleSizeChange"@current-change="handleCurrentChange"layout="prev, pager, next, jumper, ->, sizes, total"></el-pagination>
.pagination {margin-top: 20px;text-align: center;
}

day2

1.品牌管理动态数据展示

1.修改接口地址

原地址端口更改,代理跨域发生改变

proxy: {'/dev-api': {target: 'http://gmall-h5-api.atguigu.cn',pathRewrite: { '^/dev-api': '' },},},

后续就是写接口,写仓库

2.获取品牌列表接口

在api文件夹创建product文件夹统一管理商品管理的接口

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-ShFN3MJJ-1663551760269)(C:\Users\15363\AppData\Roaming\Typora\typora-user-images\image-20220916165311726.png)]

在index中统一暴露

//统一暴露
import *as tradeMark from './product/tradeMark'
import *as attr from './product/attr'
import *as sku from './product/sku'
import *as spu from './product/spu'export default {tradeMark,attr,sku,spu,
}
//获取品牌信息
export const reqTradeMarkList = (page, limit) =>request({ url: `/admin/product/baseTrademark/${page}/${limit}`, method: 'get' })

这里不需要共享数据所以没有使用vuex仓库,而是将api添加到Vue原型上,其他组件可以直接调用

import API from '@/api'
Vue.prototype.$API = API

获取数据

 mounted() {this.getPageList()},methods: {//获取商品列表async getPageList() {const { page, limit } = thislet result = await this.$API.tradeMark.reqTradeMarkList(page, limit)if (result.code == 200) {this.total = result.data.totalthis.list = result.data.records}},//点击分页器跳转页码handleCurrentChange(pager) {this.page = pagerthis.getPageList()},//展示数据条数切换handleSizeChange(sizes) {this.limit = sizesthis.getPageList()},

展示数据

elementUI当中的table组件,展示的数据是以一列一列进行展示数据的

如果需要显示索引,可以增加一列el-table-column,设置type属性为index即可显示从 1 开始的索引号。

prop:对应列内容的字段名,也可以使用 property 属性【字符串类型】

el-tabel :data="list"表示这个表格展示的是哪里面的数据

第一列 我们要展示的是序列号,可以用 type="index"表示从1 开始展示索引号

第二列 我们展示的是品牌类型,在list 里面的tmName,我们可以用prop:对应列内容的字段名

    <el-table border :data="list"><el-table-columnlabel="序号"width="80"align="center"type="index"></el-table-column><el-table-column label="品牌类型" prop="tmName"></el-table-column><el-table-column label="品牌LOGO"><!-- { row, $index }是固定的名字,不能瞎写 --><template slot-scope="{ row, $index }"><!-- row代表的是数组回传的数据 --><img :src="row.logoUrl" alt="" style="width: 100px; height: 100px" /></template></el-table-column><el-table-column label="操作"><template slot-scope="{ row, $index }"><el-button type="warning" icon="el-icon-edit>" size="mini">修改</el-button><el-button type="danger" icon="el-icon-delete>" size="mini">删除</el-button></template></el-table-column></el-table>

第三列 展示的是品牌logo,是个图片,我们有地址,我们可以用【作用域插槽】来展示图片

slot-scope="{ row, $index }"代表的是子组件回传过来的数据,也就是list

然后我们进行动态展示图片:src

分页器动态数据

    <el-pagination:current-page="page":page-sizes="[3, 5, 10]":page-size="limit"layout=" prev, pager, next, jumper,->,sizes, total":total="total"style="margin-top: 20px; text-align: center":page-count="7"></el-pagination>

完成相关点击事件

当点击页数的时候,修改data里面的page,然后再次发请求

@current-change="handleCurrentChange"当你点击其他页数时触发

    <el-pagination:current-page="page":page-sizes="[3, 5, 10]":page-size="limit"layout=" prev, pager, next, jumper,->,sizes, total":total="total"style="margin-top: 20px; text-align: center":page-count="7"@current-change="handleCurrentChange"@size-change="handleSizeChange"></el-pagination>
    // 点击页码进行切换handleCurrentChange(pager) {// pager你点击的页数// 修改参数,然后再发请求this.page = pager ;this.getPageList();},// 点击页码进行切换handleCurrentChange(pager) {// pager你点击的页数// 修改参数,然后再发请求this.page = pager ;this.getPageList();},

@size-change="handleSizeChange"当pageSize【展示数据条数】改变时触发

    // 当分页器某一页需要展示数据的条数发生变化时触发handleSizeChange(limit){// 修改数据,再次发请求this.limit = limit ;this.getPageList();},

添加和修改品牌信息(静态)

当你点击品牌管理页面 左上角【添加】的时候,会弹出一个类似遮罩层的页面

当你点击【修改】,也会弹出一个类似遮罩层的页面-----------显示对话框

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-pdAQvCLP-1663551760270)(C:\Users\15363\AppData\Roaming\Typora\typora-user-images\image-20220916172746949.png)]

我们这里用elementui的 dialog 对话框

<el-dialogtitle="添加品牌":visible.sync="dialogFormVisible"><!-- :model属性将表单数据收集到一个指定对象上 --><el-form style="width: 80%" :model="tmForm" :rules="rules" ref="ruleForm"><el-form-item label="品牌名称" label-width="100px" prop="tmName"><el-input autocomplete="off" v-model="tmForm.tmName"></el-input></el-form-item><el-form-item label="品牌logo" label-width="100px" prop="logoUrl"></el-form-item></el-form><div slot="footer" class="dialog-footer"><el-button @click="dialogFormVisible = false">取 消</el-button><el-button type="primary" @click="addOrUpdateTradeMark">确 定</el-button></div></el-dialog>

上传图片用elementui的Upload上传

 <el-uploadclass="avatar-uploader"action="/dev-api/admin/product/fileUpload":show-file-list="false":on-success="handleAvatarSuccess":before-upload="beforeAvatarUpload"><img v-if="tmForm.logoUrl" :src="tmForm.logoUrl" class="avatar" /><i v-else class="el-icon-plus avatar-uploader-icon"></i><div slot="tip" class="el-upload__tip">只能上传jpg/png文件,且不超过2M</div></el-upload>

粘贴elementui里面相关的数据和方法与样式

data(){return{dialogFormVisible: false, // 对话框显示与隐藏的控制属性imageUrl: "", // 上传图片使用的属性}
},
methods:{// 上传图片相关的回调handleAvatarSuccess(res, file) {this.imageUrl = URL.createObjectURL(file.raw);},beforeAvatarUpload(file) {const isJPG = file.type === "image/jpeg";const isLt2M = file.size / 1024 / 1024 < 2;if (!isJPG) {this.$message.error("上传头像图片只能是 JPG 格式!");}if (!isLt2M) {this.$message.error("上传头像图片大小不能超过 2MB!");}return isJPG && isLt2M;},}

3.完成 添加品牌、修改品牌和删除的功能

1.api接口

//添加或修改品牌
export const reqAddOrUpdateTradeMark = (tradeMark) => {//修改品牌信息时需要获得品牌的id,我们通过是否存在品牌id,判断需要发送什么请求if (tradeMark.id) {//修改return request({ url: '/admin/product/baseTrademark/update', method: 'put', data: tradeMark })} else {//添加return request({ url: '/admin/product/baseTrademark/save', method: 'post', data: tradeMark })}
}//删除品牌
export const reqDeleteTradeMark = (id) => request({url: `/admin/product/baseTrademark/remove/${id}`, method: 'delete'
})

2.收集数据并发请求

1收集数据

要收集到elementui里面的表单数据,就要在表单el-form上面添加 model属性,在item上添加v-model将来表单验证也需要这个属性

   <el-form style="width: 80%" :model="tmForm"><el-form-item label="品牌名称" label-width="100px" ><el-input autocomplete="off" v-model="tmForm.tmName"></el-input></el-form-item>

收集LOGO图片

这里收集数据不能使用v-model,因为不是表单元素,我们这里用了另一个el-upload

action:设置图片上传的地址

on-success 可以检测到图片上传成功,图片上传成功会执行一次

before-upload :可以在上传图片之前,会执行一次

   <el-uploadclass="avatar-uploader"action="/dev-api/admin/product/fileUpload":show-file-list="false":on-success="handleAvatarSuccess":before-upload="beforeAvatarUpload"><img v-if="tmForm.logoUrl" :src="tmForm.logoUrl" class="avatar" /><i v-else class="el-icon-plus avatar-uploader-icon"></i><div slot="tip" class="el-upload__tip">只能上传jpg/png文件,且不超过2M</div></el-upload>
 //图片上传成功handleAvatarSuccess(res, file) {//res:上传成功之后返回的前端数据//file:同上//收集品牌图片数据this.tmForm.logoUrl = res.data},//图片上传之前beforeAvatarUpload(file) {const isJPG = file.type === 'image/jpeg'const isLt2M = file.size / 1024 / 1024 < 2if (!isJPG) {this.$message.error('上传头像图片只能是 JPG 格式!')}if (!isLt2M) {this.$message.error('上传头像图片大小不能超过 2MB!')}return isJPG && isLt2M},
2发请求

当点击【添加品牌】里的【确定】按钮时

  1. 将弹出的对话框隐藏
  2. 发请求(添加品牌
  3. 如果成功,弹出一个message框:可能是添加成功,也有可能是修改成功,然后重新获取新的品牌列表
<el-button type="primary" @click="addOrUpdateTradeMark">确 定</el-button>

笔记是在中午和晚上总结的,所以步骤会有点混乱,老师是先发请求,完成功能后再完成的表单验证,这里我提前表单验证

Form 组件提供了表单验证的功能,只需要通过rules 属性传入约定的验证规则,并将 Form-Item 的 prop属性设置为需校验的字段名即可。校验规则参见 async-validator(element-ui原话)

 <el-form style="width: 80%" :model="tmForm" :rules="rules" ref="ruleForm"><el-form-item label="品牌名称" label-width="100px" prop="tmName"><el-input autocomplete="off" v-model="tmForm.tmName"></el-input></el-form-item><el-form-item label="品牌logo" label-width="100px" prop="logoUrl">
data(){return{//表单验证规则rules: {tmName: [//required:必须验证的字段,message:提示信息,trigger:用户行为,blur失焦,change发生改变{ required: true, message: '请输入品牌名称', trigger: 'blur' },{min: 2, //字符长度max: 10,message: '长度在 2 到 10 个字符',trigger: 'change',},],//图片格式、大小不在这里验证,因为他不是表单元素, 在beforeAvatarUpload方法中有校验规则logoUrl: [{ required: true, message: '请上传品牌logo' }],},
}
}

发请求

addOrUpdateTradeMark() {//当全部字段验证通过在执行操作this.$refs.ruleForm.validate(async (valid) => {if (valid) {this.dialogFormVisible = false//发请求let result = await this.$API.tradeMark.reqAddOrUpdateTradeMark(this.tmForm)if (result.code == 200) {//element-ui的消息提示this.$message({message: this.tmForm.id ? '修改品牌成功' : '添加品牌成功',type: 'success',})//判断是修改还是添加操作,修改则留在当前页,添加返回第一页this.handleCurrentChange(this.tmForm.id ? this.page : 1)this.getPageList()}} else {this.$message.error('信息未填写完整')return false}})},

完善效果,点击不同按钮显示不同

<el-dialog:title="tmForm.id ? '修改品牌' : '添加品牌'":visible.sync="dialogFormVisible">

3.删除

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-vpQNW8Hi-1663551760271)(C:\Users\15363\AppData\Roaming\Typora\typora-user-images\image-20220919094028254.png)]

当点击【删除】按钮时,会弹出一个弹框【确定要删除吗】,然后有【确定】和【取消】两个按钮

点击【删除】按钮,给【删除】绑定点击事件deleteTradeMark,要传参数(你点击该品牌的信息—row)

弹出一个弹框,里面是【确定删除】还是【取消】

确定后,发请求删除该品牌,然后再发请求获取品牌列表数据;

 deleteTradeMark(row) {this.$confirm(`确定删除${row.tmName}, 是否继续?`, '提示', {confirmButtonText: '确定',cancelButtonText: '取消',type: 'warning',})//点击确定触发.then(async () => {let result = await this.$API.tradeMark.reqDeleteTradeMark(row.id)if (result.code == 200) {this.$message({type: 'success',message: '删除成功!',})this.handleCurrentChange(this.list.length > 1 ? this.page : this.page - 1)this.getPageList()}})//点击取消触发.catch(() => {this.$message({type: 'info',message: '已取消删除',})})},

】绑定点击事件deleteTradeMark,要传参数(你点击该品牌的信息—row)

弹出一个弹框,里面是【确定删除】还是【取消】

确定后,发请求删除该品牌,然后再发请求获取品牌列表数据;

 deleteTradeMark(row) {this.$confirm(`确定删除${row.tmName}, 是否继续?`, '提示', {confirmButtonText: '确定',cancelButtonText: '取消',type: 'warning',})//点击确定触发.then(async () => {let result = await this.$API.tradeMark.reqDeleteTradeMark(row.id)if (result.code == 200) {this.$message({type: 'success',message: '删除成功!',})this.handleCurrentChange(this.list.length > 1 ? this.page : this.page - 1)this.getPageList()}})//点击取消触发.catch(() => {this.$message({type: 'info',message: '已取消删除',})})},

后续不想写了,主要是没那么多时间整理,只能写在代码注释里,抱歉。
完成后的GitHub源码地址
码云地址

尚硅谷的后台管理系统学习笔记【尚硅谷】【Vue】相关推荐

  1. MySQL学习笔记——尚硅谷李玉婷经典版MySQL基础笔记(一)

    MySQL学习笔记--尚硅谷李玉婷经典版MySQL基础笔记(一) MySQL学习笔记目录 MySQL学习笔记--尚硅谷李玉婷经典版MySQL基础笔记(一) 一.基础知识 1.MySQL的语法规范 2. ...

  2. maven学习笔记——尚硅谷

    文章目录 maven学习笔记--尚硅谷 第一章 Maven概述 第一节 为什么要学习Maven 1.Maven 作为依赖管理工具 1.1 jar 包的规模 1.2 jar 包的来源 1.3 jar 包 ...

  3. 「Vue 学习笔记 1」Vue 项目快速搭建,初始项目各个文件夹作用介绍和启动代码执行流程分析

    「Vue 学习笔记 1」Vue 项目快速搭建,初始项目各个文件夹作用介绍和启动代码执行流程分析 前言 一.我的开发环境 二.使用 Vue CLI (Vue 脚手架)快速搭建项目 三.初始项目的目录结构 ...

  4. Rabbitmq学习笔记(尚硅谷2021)

    Rabbitmq学习笔记 (尚硅谷) 1.MQ 的概念 1.1 什么是 MQ? 1.2 为什么要用 MQ? 削峰 解耦 异步 1.3 MQ 的分类 ActiveMQ Kafka RocketMQ Ra ...

  5. 尚硅谷springboot 2核心技术学习笔记

    开发前先查看系统Java和maven的版本 参考资料 1.尚硅谷/SpringBoot2核心技术与响应式编程 2.springboot官网 3.版本升级变化 maven环境配置 <mirrors ...

  6. 【HBase学习笔记-尚硅谷-Java API shell命令 谷粒微博案例】

    HBase学习笔记 HBase 一.HBase简介 1.HBase介绍 2.HBase的逻辑结构和物理结构 3.数据模型 4.基本架构 二.快速入门 1.配置HBase 2.命令 三.API 1.获取 ...

  7. SpringBoot练手项目《尚硅谷智慧校园》学习笔记

    ​ 一 项目展示 1 登录及角色控制 ​ 2首页展示 3 业务模块展示 二 智慧校园系统简介 2.1 项目简介 智慧校园管理系统:主要是以年级.班级为单位,进行老师和学生信息记录和统计功能.项目采用前 ...

  8. 【尚硅谷/周阳】JUC学习笔记

    JUC学习笔记[尚硅谷/周阳] 本文章基于B站视频教程[juc 与 jvm 并发编程 Java 必学_阳哥- 尚硅谷]进行整理记录,仅用于个人学习,交流使用. 目录标题 JUC学习笔记[尚硅谷/周阳] ...

  9. 尚硅谷Spring注解开发学习笔记

    文章目录 前言 1.课程安排 1.1.容器 1.2.扩展原理 1.3.Web 2.配置文件开发 2.1.导入Spring-context依赖包 2.2.编写Spring配置文件 2.3.编写Perso ...

最新文章

  1. 有了易生信,导师再也不用担心我的单细胞转录组整合分析啦
  2. 小小flash动画_flash宣传动画视频能给公司品牌传播带来什么
  3. Creational模式之Builder模式
  4. 春运背后默默守护高铁安全的“隐形人”
  5. 自定义变量 配置文件_「系统架构」Nginx调优之变量的使用(3)
  6. Mathemmatica 新函数
  7. 【Java 数据库】Connections.getTables() 方法 获取数据库的元数据
  8. java对类数组进行排序_Java比较器类对数组进行排序
  9. slitaz c语言开发环境,makefile和cmake的简单使用
  10. Maya中AO贴图的一些烘焙心得
  11. 计算机方面的英语学术期刊,近几年计算机专业英文参考文献 计算机专业英文核心期刊参考文献有哪些...
  12. 计算机职业适应性测试题库,职业适应性测试题库 一、性格职业适应度测试.doc...
  13. 六千档最强万金油?华硕无畏Pro15 2022锐龙版笔记本体验
  14. win10服务器cpu占用过高,解决win10服务主机内存和cpu高占用的解决方法
  15. Java中String类intern()详解
  16. 老说程序员如何看产品经理,今天说说产品经理讨厌哪些程序员
  17. 尚医通(九)数据字典模块前后端 | EasyExcel
  18. 51单片机 玩转按键加减切换+数码管+Proteus仿真
  19. 3、Mybatis-Plus异常之There is no getter for property named ‘ew‘ in ‘class解决方案
  20. SPDR年内增量尽数被抹 市场看空金市

热门文章

  1. 【Magicavoxel简易入门教程】(二) 第二章 · 自制一个NPC导出模型优化工具使用(附下载)
  2. JDK8之ConcurrentHashMap源码解读
  3. 详解办公室装修设计省钱妙计
  4. 办公室设计公司关于办公室装修全过程解剖
  5. python argparse 和opencv模块的组合使用_如何利用Python3和OpenCV对比两张图片的不同,提取差异性...
  6. JMeter基础系列(八) JMeter断言之JSON断言
  7. 送给大一新生的一些话
  8. 京东技术体系员工级别划分及薪资区间
  9. 联想拯救者R720重装Win10系统的正确姿势
  10. 【转】2018年EI收录中文期刊目录