通过属性值从深度嵌套的对象数组中删除对象

时间:2020-07-10 04:36:09

标签: javascript arrays typescript object filter

考虑一下,我有一个嵌套的对象数组。一种可能的示例场景是:

content: [
    {
        prop1: someValue,
        prop2: someValue,
        content: [
            {
                prop2: someValue,
                prop3: someValue,
                myProperty: myValue
            },
            {
                prop1: someValue,
                prop3: someValue,
                myProperty: otherValue
            }
        ]
    },
    {
        prop5: someValue,
        prop2: someValue
    }
]

这里是可能性:

  • 结构以content[]开头,但后代可能具有或不具有content属性。
  • 层次结构的级别可以是任意数量。
  • 对象包含的属性并不总是相同的,即一个对象可能具有x,y,z属性,而另一个对象可能具有v,w,z属性。
  • 如果层次结构中的任何对象都具有myProperty键,则不会有content键。
  • 层次结构中的多个对象可以具有值myProperty的{​​{1}}。

我的要求:

  • 如果在任何级别上对象都具有值为'myValue的属性myProperty,则从层次结构中删除整个对象(不只是属性)。

到目前为止,我的尝试:

myValue

4 个答案:

答案 0 :(得分:1)

以下内容递归地返回一个新数组,而不改变原始数组

const content = [{
    prop1: "someValue",
    prop2: "someValue",
    content: [{
        prop2: "someValue",
        prop3: "someValue",
        myProperty: "myValue"
      },
      {
        prop1: "someValue",
        prop3: "someValue",
        myProperty: "otherValue"
      }
    ]
  },
  {
    prop5: "someValue",
    prop2: "someValue"
  }
]

function removeObjects(content) {
  return content.reduce((arr, obj) => {
    if (obj["myProperty"] && obj["myProperty"] === "myValue") {
      return arr
    } else if (obj["content"] && obj["content"].length) {
      arr.push({ ...obj,
        content: removeObjects(obj["content"])
      })
      return arr
    } else {
      arr.push(obj);
      return arr;
    }
  }, []);
}



console.log(removeObjects(content))

预期输出:

const content = [{
        prop1: "someValue",
        prop2: "someValue",
        content: [
          {
            prop1: "someValue",
            prop3: "someValue",
            myProperty: "otherValue"
          }
        ]
      },
      {
        prop5: "someValue",
        prop2: "someValue"
      }
    ]

答案 1 :(得分:0)

尝试一下(这是JavaScript版本)

    let someValue = 'a';
    let otherValue ='x';
    let myValue = 'xy';
    let content = [
        {
            prop1: someValue,
            prop2: someValue,
            content: [
                {
                    prop2: someValue,
                    prop3: someValue,
                    myProperty: myValue
                },
                {
                    prop1: someValue,
                    prop3: someValue,
                    myProperty: otherValue
                }
            ]
        },
        {
            prop5: someValue,
            prop2: someValue
        }
    ];


     function removeObjects(content, values) {
         debugger;
        if (!content || content.length === 0) {
          return
        }
        content = content.filter((c) => {
          if (!c.myProperty) return true
           return c.myProperty.indexOf(values) > 0
        })
        // Here is my problem since I am supposed to do a recursive call on each of child contents,
        // how do I merge back the original array?
        return content.map(x => ({
            ...x,
            content: removeObjects(x.content, values)
        }))
      }

      console.log(removeObjects(content, 'x'))

答案 2 :(得分:0)

您可以使用以下功能获得预期结果:

let data = {
    content: [
        {
            prop1: 'someValue',
            prop2: 'someValue',
            content: [
                {
                    prop2: 'someValue',
                    prop3: 'someValue',
                    myProperty: 'myValue'
                },
                {
                    prop1: 'someValue',
                    prop3: 'someValue',
                    myProperty: 'otherValue'
                }
            ]
        },
        {
            prop5: 'someValue',
            prop2: 'someValue'
        }
    ]
}

function removeMyvalyeObj(data) {
    for (let i = data.content.length - 1; i >= 0; i--) {
        if (data.content[i].myProperty === 'myValue') {
            data.content.splice(i, 1);
        } else if(data.content[i].content) {
            removeMyvalyeObj(data.content[i])
        }
    }
}

removeMyvalyeObj(data);
console.log(data);

答案 3 :(得分:0)

使用递归方法,以拥有val builder = AlertDialog.Builder(activity as Context) .setTitle("Confirmation") .setMessage("Are you sure you want to log out?") .setPositiveButton("YES"){ dialog, _ -> sharedPreferences.edit().clear().apply() println("Shared preferences cleared") println("Logged out") dialog.dismiss() val intent = Intent(activity as Context, LoginActivity::class.java) startActivity(intent) } .setNegativeButton("NO"){dialog,_ -> val homeFragment = HomeFragment() val beginTransaction = activity!!.supportFragmentManager.beginTransaction() beginTransaction.replace(R.id.frameLayout, homeFragment) dialog.dismiss() beginTransaction.commit() activity!!.navigationView.setCheckedItem(R.id.home_screen) println("Home title set") activity!!.actionBar!!.title = "Home" } .show() 个项目数组及其filter数组。

content