Javascript 即使使用“扩展”操作符,组件渲染函数中也可能存在无限更新循环
我知道这个问题以前已经得到了回答,但在查看之后,我发现解决方案不起作用 有人能帮我弄清楚这是怎么回事吗Javascript 即使使用“扩展”操作符,组件渲染函数中也可能存在无限更新循环,javascript,vue.js,Javascript,Vue.js,我知道这个问题以前已经得到了回答,但在查看之后,我发现解决方案不起作用 有人能帮我弄清楚这是怎么回事吗 <template> <div> <template v-for="listing in sortedListings"> <listing :key="listing.uuid" :listing="listing" :
<template>
<div>
<template v-for="listing in sortedListings">
<listing
:key="listing.uuid"
:listing="listing"
:highlight-color="listing.highlight ? getHighlightColor() : null"
/>
</template>
</div>
</template>
<script>
import Listing from '@/components/Listing'
export default {
components: {
Listing,
},
data: function () {
return {
highlightColors: this.getHighlightColors(),
listings: [
{
uuid: '658f325f-33c8-455b-98f6-27eb4eaa16a0',
title: 'Cursus Nullam Amet Tortor',
location: 'Remote',
url: 'http://example.net/birds',
hours_week: 20,
tags: ['django', 'python', 'flask'],
logo: 'https://logo.clearbit.com/apple.com',
company_name: 'Apple',
show_logo: 1,
highlight: 0,
stick_top: 0,
},
{
uuid: '658f325f-33c8-455b-98f6-27eb4eaa16a1',
title: 'Donec id elit non mi porta gravida at eget metus',
location: 'Remote',
url: 'http://example.net/birds',
hours_week: 20,
tags: ['django', 'python', 'flask', 'full-stack', 'contract'],
logo: 'https://logo.clearbit.com/apple.com',
company_name: 'Mapple',
show_logo: 0,
highlight: 0,
stick_top: 0,
},
{
uuid: '658f325f-33c8-455b-98f6-27eb4eaa16a2',
title:
'Donec ullamcorper nulla non metus auctor fringilla ullamcorper dapibus',
location: 'Remote / USA',
url: 'http://example.net/birds',
hours_week: 20,
tags: ['django', 'python', 'flask', 'full-stack', 'vue.js'],
logo: 'https://logo.clearbit.com/apple.com',
company_name: 'Fapple',
show_logo: 1,
highlight: 0,
stick_top: 1,
},
{
uuid: '658f325f-33c8-455b-98f6-27eb4eaa16a3',
title: 'Tristique Euismod Venenatis Porta',
location: 'San Francisco, CA, USA',
url: 'http://example.net/birds',
hours_week: 20,
tags: ['django', 'python', 'flask', 'full-stack', 'vue.js'],
logo: 'https://logo.clearbit.com/apple.com',
company_name: 'Lapple',
show_logo: 1,
highlight: 1,
stick_top: 0,
},
{
uuid: '658f325f-33c8-455b-98f6-27eb4eaa16a4',
title: 'Tristique Euismod Venenatis',
location: 'San Francisco, CA, USA',
url: 'http://example.net/birds',
hours_week: 20,
tags: ['django', 'python', 'flask', 'full-stack', 'vue.js'],
logo: 'https://logo.clearbit.com/apple.com',
company_name: 'Dapple',
show_logo: 1,
highlight: 1,
stick_top: 1,
},
],
}
},
computed: {
sortedListings: function () {
return [...this.listings].sort(function (a, b) {
return b.stick_top - a.stick_top
})
},
},
methods: {
getListings: async function () {},
getHighlightColors: function () {
return this.shuffleArray([
'#E3F2FD',
'#E8EAF6',
'#FFEBEE',
'#E0F2F1',
'#E8F5E9',
'#FFF3E0',
'#FFFDE7',
])
},
getHighlightColor: function () {
if (this.highlightColors.length === 0) {
this.highlightColors = this.getHighlightColors()
}
return this.highlightColors.shift()
},
},
mounted: function () {
this.getListings()
},
}
</script>
从“@/components/Listing”导入列表
导出默认值{
组成部分:{
表册
},
数据:函数(){
返回{
highlightColors:this.getHighlightColors(),
清单:[
{
uuid:'658f325f-33c8-455b-98f6-27eb4eaa16a0',
标题:“侵权者之咒”,
位置:'远程',
网址:'http://example.net/birds',
每周工作时数:20,
标记:['django','python','flask'],
标志:'https://logo.clearbit.com/apple.com',
公司名称:“苹果”,
show_logo:1,
推荐理由:0,
棒顶:0,
},
{
uuid:'658f325f-33c8-455b-98f6-27eb4eaa16a1',
标题:“在eget metus的Donec id elit非mi porta孕妇”,
位置:'远程',
网址:'http://example.net/birds',
每周工作时数:20,
标记:['django','python','flask','full stack','contract'],
标志:'https://logo.clearbit.com/apple.com',
公司名称:“Mapple”,
显示\u徽标:0,
推荐理由:0,
棒顶:0,
},
{
uuid:'658f325f-33c8-455b-98f6-27eb4eaa16a2',
标题:
“Donec ullamcorper nulla non metus拍卖商fringilla ullamcorper dapibus”,
位置:“远程/美国”,
网址:'http://example.net/birds',
每周工作时数:20,
标签:['django','python','flask','full stack','vue.js'],
标志:'https://logo.clearbit.com/apple.com',
公司名称:“Fapple”,
show_logo:1,
推荐理由:0,
杆顶:1,
},
{
uuid:'658f325f-33c8-455b-98f6-27eb4eaa16a3',
标题:“特里斯蒂克·尤伊斯莫·维尼纳蒂斯门”,
地点:美国加利福尼亚州旧金山,
网址:'http://example.net/birds',
每周工作时数:20,
标签:['django','python','flask','full stack','vue.js'],
标志:'https://logo.clearbit.com/apple.com',
公司名称:“Lapple”,
show_logo:1,
亮点:一,,
棒顶:0,
},
{
uuid:'658f325f-33c8-455b-98f6-27eb4eaa16a4',
标题:“特里斯蒂克·尤伊斯莫·维内纳蒂斯”,
地点:美国加利福尼亚州旧金山,
网址:'http://example.net/birds',
每周工作时数:20,
标签:['django','python','flask','full stack','vue.js'],
标志:'https://logo.clearbit.com/apple.com',
公司名称:“Dapple”,
show_logo:1,
亮点:一,,
杆顶:1,
},
],
}
},
计算:{
分类列表:函数(){
return[…this.listings].sort(函数(a,b){
返回b.斗杆顶部-a.斗杆顶部
})
},
},
方法:{
getListings:async函数(){},
GetHighlightColor:函数(){
把这个还给我([
“#E3F2FD”,
“#E8EAF6”,
#FFEBEE",,
“#E0F2F1”,
"E8F5E9",,
"FFF3E0",,
"FFFDE7",,
])
},
getHighlightColor:函数(){
if(this.highlightColors.length==0){
this.highlightColors=this.getHighlightColors()
}
返回此.highlightColors.shift()
},
},
挂载:函数(){
这个文件名为getListings()
},
}
在computed属性
sortedListings
中,我已经在执行[…this.listings]
扩展运算符不会深度克隆数组,排序方法会修改生成无限循环的computed中使用的原始属性,因此添加一个方法来深度克隆对象,如:
spread操作符不会深度克隆数组,而sort方法会修改生成无限循环的computed中使用的原始属性,因此请添加一个方法来深度克隆对象,如下所示:
getHighlightColor()
导致无限循环
这是一个典型的例子,说明了为什么绑定到模板中的方法是不好的(并非总是如此)。如果您的方法更改了模型,Vue必须重新加载组件。然后触发该方法并再次更改模型,从而导致组件重新加载,依此类推
此演示将产生相同的结果,但如果改用模板中的计算结果,则不会产生相同的结果:
newvue({
el:“应用程序”,
数据(){
返回{
arr:[1,2,3,4,5]
}
},
方法:{
更改:函数(){
返回此.arr.shift();
},
},
计算:{
测试(){
返回此.arr.shift();
}
}
});代码>
{{change()}}
getHighlightColor()
导致无限循环
这是一个典型的例子,说明了为什么绑定到模板中的方法是不好的(并非总是如此)。如果您的方法更改了模型,Vue必须重新加载组件。然后触发该方法并再次更改模型,从而导致组件重新加载,依此类推
此演示将产生相同的结果,但如果改用模板中的计算结果,则不会产生相同的结果:
newvue({
el:“应用程序”,
数据(){
返回{
arr:[1,2,3,4,5]
}
},
方法:{
更改:函数(){
返回此.arr.shift();
},
},
计算:{
测试(){
返回此.arr.shift();
}
}
});代码>
{{change()}}
刚刚试过。不起作用:(只是尝试了一下。不起作用:(我明白你的意思。我只是将computed属性更改为一个方法。但是我仍然得到了错误。你已经得到了错误。你必须将该方法更改为ComputedWhat方法?抱歉getHighlightColor()
@JacobHyde我没有重现代码,我集中精力
...
computed: {
sortedListings: function () {
return this.deepCopy(this.listings).sort(function (a, b) {
return b.stick_top - a.stick_top
})
},
},
methods: {
deepCopy(src) {
let target = Array.isArray(src) ? [] : {};
for (let prop in src) {
let value = src[prop];
if(value && typeof value === 'object') {
target[prop] = deepCopy(value);
} else {
target[prop] = value;
}
}
return target;
}
,
getListings: async function () {},
...