【问题标题】:Problem in adding object properties to specific object inside array in JavaScript将对象属性添加到 JavaScript 中数组内的特定对象的问题
【发布时间】:2019-09-20 06:09:14
【问题描述】:

我在 JavaScript 中有一个看起来像这样的对象

{
product_id: "2",
product_name: "Drinks"
}

对象的名称是product。

有一个包含上述对象条目的数组。因此,每个数组项都是上述对象的一个​​条目。

单击按钮时,我检查数组中是否存在具有特定 product_id(正在搜索)的对象条目。如果数组中不存在具有特定 product_id 的对象,那么我必须将此新对象添加到数组中。而如果具有特定 product_id 的对象条目存在,那么首先我向对象添加一个名为“qty”的新属性,然后将该对象作为新条目添加到数组中。

下面是按钮点击的代码。

我使用console.log() 数组来查看结果。

当第一次单击按钮时,我会正确地获取数组条目,它显示数组中的对象。

当第二次单击按钮时,代码进入 else 条件,并将一个新属性(名称为 qty)添加到对象中,然后将对象添加到数组中。所以,现在数组有两个对象条目(第一个是通过 if 条件添加的,第二个是通过 else 条件添加的)。

奇怪的是,问题在于,当第二次单击按钮并执行 else 条件时,代码会修改先前存在的对象条目(数组中已经存在)并在该对象条目中添加 qty 属性.

理想情况下,它应该将这两个视为单独的条目,如果我修改第二个对象条目,那么第一个条目(已经存在于数组中)应该保持原样(这意味着没有 qty 属性),而它会修改前一个条目也添加了新的。

OnButtonClick() {
  if (array.length === 0) {
    array.splice(0, 0, product);
  }
  else {
    product.qty = 1;
    array.splice(0, 0, this.product);
  }
}

以下是完整代码:

// First Page: categories.ts sets the existing product object using a service 
// then navigates to the second page product.ts
ButtonClick() {
    this.Service.setProduct(product);
    this.route.navigate(['products']);
}

// Service page: service.ts

export class ManageService {
    products: any;
    ProductArray: any = [];

    constructor() { }
    public setProduct(data) {
      this.products = data;
    }

    public getProduct() {
        return this.products;
    }
}

//Second page: products.ts
// First it gathers the product object details that were passed from previous 
// categories.ts using getProduct() method in the service.ts 

export class ProductsPage implements OnInit {
    product: any = [];

    ngOnInit() {
        this.product = this.Service.getExtras();
    }

    ButtonClick(searchid: any) {
        // searchid is passed on button click
        let findsearchidarr = FindItem(searchid);
        if (findsearchidarr[0] === true) {
            this.Service.ProductArray[findsearchidarr[1]].quantity = 
++this.Service.ProductArray[findsearchidarr[1]].quantity;
            this.router.navigate(['categories']);
        }
        else if (findsearchidarr[0] === false) {
            this.product.quantity = 1;
            this.Service.ProductArray.splice(0, 0, this.product);
            this.router.navigate(['categories']);
        }
    }
FindItem (searchid: any) {
        let i = 0;
        let foundarray: any = [];

        for (let items of this.Service.ProductArray) {
        if (items.search_id.toLowerCase().includes(searchid)) {
            foundarray[0] = true;
            foundarray[1] = i;
            foundarray[2] = items.product_id;
            return foundarray;
        }
        i++;
        }
        foundarray[0] = false;
        foundarray[1] = -1;
        foundarray[2] = 0;
        return foundarray;
    }
}

【问题讨论】:

  • 该方法的逻辑有问题。你甚至没有检查product_id 是否存在?
  • 对于if 条件,您在哪里声明product?应该是this.product
  • @JasonWhite:是的,就是这个产品
  • @wentjun 我忽略了那部分以简化代码,以便专注于核心问题
  • 能把所有的代码都加进去吗?

标签: javascript arrays angular javascript-objects


【解决方案1】:

请参阅下面的逻辑。它将数量属性添加到现有对象,否则将新对象添加到数组。

products: any[] = [{
    product_id: "2",
    product_name: "Drinks"
  },
  {
    product_id: "3",
    product_name: "Wafers"
  },
  {
    product_id: "4",
    product_name: "Chocolates"
  }
];

productIDToSearch:number = 4;
quantityToAdd: number = 20;
let foundIndex = products.findIndex((val) => val.product_id == productIDToSearch);

if(this.foundIndex >= 0) {
    this.products[this.foundIndex].quantity = this.quantityToAdd;
}
else {
    this.products.push({product_id:productIDToSearch, product_name:'Ice-cream', quantityToAdd: 33});
    console.log(products);
}

等效的javascript代码

var products = [{
    product_id: "2",
    product_name: "Drinks"
  },
  {
    product_id: "3",
    product_name: "Wafers"
  },
  {
    product_id: "4",
    product_name: "Chocolates"
  }
];

let productIDToSearch = 5;
let quantityToAdd = 20;
let foundIndex = products.findIndex((val) => val.product_id == productIDToSearch);

if(foundIndex >= 0) {
	products[foundIndex].quantity = quantityToAdd;
  console.log(products);
}
else {
	products.push({product_id:productIDToSearch, product_name:'Ice-cream', quantityToAdd: 33});
  console.log(products);
}

【讨论】:

  • Saksham - 我对我的帖子进行了编辑并包含了我的完整代码,你可以看到我已经在遵循类似的方法,在那里我找到了所需条目的索引,如果我找不到那么我添加了一个新条目,但是奇怪的是,当我创建一个新条目时,它也会覆盖前一个条目的数量。
【解决方案2】:

问题在于,在 JavaScript 中对象是通过引用处理的,因此当我尝试在对象数组中添加任何属性或修改任何属性时,它会造成混乱(至少在我的情况下)。

我找到的解决方案是先将对象复制到另一个对象,这样就排除了“通过引用”的可能性,然后使用新的“复制”对象来标记一个新条目。这解决了问题。

【讨论】:

  • 数组在 javascript 中也是通过引用传递的。它们在您传递给它们的任何范围内都是完全可变的。
猜你喜欢
  • 1970-01-01
  • 2021-03-22
  • 1970-01-01
  • 2016-07-26
  • 2022-06-27
  • 2011-11-09
  • 2015-11-15
  • 2022-12-05
相关资源
最近更新 更多