【问题标题】:Vue.js - Unique values from an array through a computed propertyVue.js - 通过计算属性从数组中获取唯一值
【发布时间】:2019-12-19 20:01:03
【问题描述】:

我正在使用计算属性来过滤一个值数组,并从数组中只提取一组唯一项。最初我只需要一个变量,但现在我需要用它来提取两个不同的值,并且在创建两个计算属性时无法让它彼此独立工作。

这是我的 Vue HTML 代码:

<div v-for="item in getUniques">
<input :value="item.car" v-model="selectedCars" type="checkbox">
<label>&nbsp;{{item.car}}</label>
</div>

函数如下:

 data(){
      return {

selectedCars: [],
prefetch: [
           {car: "XC90", brand: "Volvo"},
           {car: "XC60", brand: "Volvo"},
           {car: "XC90", brand: "Volvo"},
           {car: "X-Type", brand: "Jaguar"}   
          ]
 }
},


computed: {

getUniques(){

                return this.prefetch.reduce((seed, current) => {

                    return Object.assign(seed, {
                        [current.car]: current
                    });

                }, {});

            },

}


// This works perfectly for pulling out the unique values of cars and returns... [XC90,XC60, X-Type] 

但是当我尝试创建另一个计算属性来做同样的事情,但只与 brands 一起工作时,一切都会中断并且我无法定义。如何调整这个计算属性,以便过滤掉这个数组中的所有其他唯一值?

我已经尝试了所有方法,但无法解决。提前感谢您的帮助!!

【问题讨论】:

  • 所以用[current.brand] 替换[current.car] 会给你一个错误?
  • 如果我独立运行它不会,但是当我尝试在计算的同时运行它们时会引发错误。我知道不建议将逻辑添加到计算属性中,所以我一直在弄清楚从那里去哪里
  • 我对为什么会发生这种情况很感兴趣。我不相信 .reduce()prefetch 对象有什么奇怪的地方,但显然当多个计算属性使用同一个对象时它会中断?
  • 正确。切换到下面@Daniel 推荐的映射函数实际上可以同时运行多个计算属性。我仍然很想知道是否有一种方法可以沿单个计算属性进行流式传输,而不是随着样本数组大小的增长而不得不维护多个单个映射函数
  • 计算属性缓存它们的输出。他们根据内容创建依赖关系列表,并且只有在感知依赖关系发生变化时才会重新计算。您可以尝试两件事 - 1)使独特的属性更加明显。这可能有点hacky。 2) 返回一个采用唯一属性名称的函数,在这种情况下,该函数被缓存但每次调用时都能正常工作。这可以更简单地作为方法而不是计算属性来完成。

标签: javascript vue.js


【解决方案1】:

对于唯一性的基本检查

对于像这样的数组:

let prefetch = [
  {car: "XC90", brand: "Volvo"},
  {car: "XC60", brand: "Volvo"},
  {car: "XC90", brand: "Volvo"},
  {car: "X-Type", brand: "Jaguar"}   
 ]

您可以使用此处所述的 2 过滤功能:Get all unique values in a JavaScript array (remove duplicates)

let prefetch = [
  {car: "XC90", brand: "Volvo"},
  {car: "XC60", brand: "Volvo"},
  {car: "XC90", brand: "Volvo"},
  {car: "X-Type", brand: "Jaguar"}   
 ]

 function getUniqueCars() {
   return prefetch.map(x => x.car).filter((v,i,s) => s.indexOf(v) === i)
 }

 function getUniqueBrands() {
  return prefetch.map(x => x.brand).filter((v,i,s) => s.indexOf(v) === i)
 }

 console.log(getUniqueCars())
 console.log(getUniqueBrands())

这也可以用作 vue 中的计算函数...

vue使用临时Array的解决方案

另一种解决方案可能是创建一个临时数组来计算您想要使用的独特汽车/品牌对...

let vm = new Vue({
  el: '#app',
  data() {
    return {
      selectedCars: [],
      prefetch: [{
          car: "XC90",
          brand: "Volvo"
        },
        {
          car: "XC60",
          brand: "Volvo"
        },
        {
          car: "XC60",
          brand: "Volvo"
        },
        {
          car: "XC90",
          brand: "Volvo"
        },
        {
          car: "X-Type",
          brand: "Jaguar"
        }
      ]
    }
  },
  computed: {
    getUniques() {
      let tempArray = [];
      for (let item of this.prefetch) {
        (tempItem => {
          if (!(tempItem.length > 0 && tempItem.find(x => x.brand === item.brand))) tempArray.push(item);
        })(tempArray.filter(x => x.car === item.car))
      }
      return tempArray;
    }
  }
})
<div id="app">
  <div v-for="item in getUniques">
    <input :value="item.car" v-model="selectedCars" type="checkbox">
    <label>&nbsp;{{item.brand}} {{item.car}}</label>
  </div>
</div>

<script src="https://cdnjs.cloudflare.com/ajax/libs/vue/2.5.17/vue.js"></script>

【讨论】:

  • 谢谢!这行得通。但是,我仍然想知道是否有办法通过将所有内容都变成单个计算属性来减少函数数量,因为我正在使用的数组非常大
  • 我(不进行重构)将构建一个 tempArray 来计算唯一性,例如 function getUniques() { let tempArray = []; for(let item of prefetch) { (tempItem =&gt; { if(!(tempItem.length &gt; 0 &amp;&amp; tempItem.find(x =&gt; x.brand === item.brand))) tempArray.push(item); })(tempArray.filter(x =&gt; x.car === item.car)) } return tempArray; }
  • 最后一条评论可能作为一个单独的计算结果可以正常工作 - 为什么不将它添加到答案正文中以更清晰,并显示模板如何使用它?
  • @RichardMatsen 感谢您的建议。我使用临时数组添加了另一个解决方案。
【解决方案2】:

你可以使用 lodash 的 uniq

然后做

return _.uniqBy(this.prefetch, 'car');

【讨论】:

  • Computed Caching vs Methods,这可能没有帮助。
  • @RichardMatsen 除非我误解了他的问题,缓存版本应该没问题吗?我仍然有点不清楚他的独特性标准是什么
  • 确实,我对 al2xs 想要看到的最终模式感到困惑。请注意,他将来需要使用 carbrand 以及其他标准。唯一值必须被视为反应性依赖,因此字符串文字不符合条件。在单独的数据属性中设置car 可以解决问题,但在模板中实现它有点嘈杂且难以实现。方法是更好的方法,因为方法不缓存。
猜你喜欢
  • 2017-06-20
  • 2019-08-08
  • 1970-01-01
  • 1970-01-01
  • 2017-11-09
  • 2016-12-12
  • 2020-12-12
  • 2018-11-27
  • 2020-11-13
相关资源
最近更新 更多