在对象数组中搜索匹配的属性和值对

时间:2016-01-20 12:08:54

标签: javascript

我正在尝试解决freeCodeCamp练习并且卡住了。练习的目标是:创建一个查看对象数组(第一个参数)的函数,并返回具有匹配的属性和值对(第二个参数)的所有对象的数组。如果要包含在返回的数组中,源对象的每个属性和值对都必须存在于集合中的对象中。

所以我做的是制作一个集合的密钥对数组,以及另一个带有密钥对的数组。 I嵌套for循环以查找匹配的键,如果找到这些键,则比较属性。

但不知何故,我的代码没有返回匹配。

Public Sub Main()

    Dim oXL As Object
    Dim oWrkBk As Object
    Dim oWrkSht As Object
    Dim oRng As Object

    Set oXL = CreateXL
    Set oWrkBk = oXL.workbooks.Open("<path and workbook name>.xlsx")
    Set oWrkSht = oWrkBk.Worksheets("<sheet name>")
    Set oRng = oWrkSht.range("A1")

    'Select the range.
        'oWrkSht.select
        'oRng.select

    'Go to the range.
        'oXL.Goto Reference:=oWrkSht.range("A1"), Scroll:=True

    'Do stuff with the range (no need to select it).
    oRng.Value = "10"
    MsgBox oRng.Address & " has the value of " & oRng.Value

End Sub

Public Function CreateXL(Optional bVisible As Boolean = True) As Object

    Dim oTmpXL As Object

    '''''''''''''''''''''''''''''''''''''''''''''''''''''
    'Defer error trapping in case Excel is not running. '
    '''''''''''''''''''''''''''''''''''''''''''''''''''''
    On Error Resume Next
    Set oTmpXL = GetObject(, "Excel.Application")

    '''''''''''''''''''''''''''''''''''''''''''''''''''''''
    'If an error occurs then create an instance of Excel. '
    'Reinstate error handling.                            '
    '''''''''''''''''''''''''''''''''''''''''''''''''''''''
    If Err.Number <> 0 Then
        Err.Clear
        On Error GoTo ERROR_HANDLER
        Set oTmpXL = CreateObject("Excel.Application")
    End If

    oTmpXL.Visible = bVisible
    Set CreateXL = oTmpXL

    On Error GoTo 0
    Exit Function

ERROR_HANDLER:
    Select Case Err.Number

        Case Else
            MsgBox "Error " & Err.Number & vbCr & _
                " (" & Err.Description & ") in procedure CreateXL."
            Err.Clear
    End Select

End Function

有人可以指出我做错了吗?

如果你想修补,我还创建了一个JSfiddle

6 个答案:

答案 0 :(得分:2)

在声明中更明确 - 有助于更轻松地阅读代码:

viewConfig: {
        preserveScrollOnReload: true
 }

https://jsfiddle.net/fullcrimp/1cyy8z64/

答案 1 :(得分:2)

当我偶然发现一些资源来帮助时,我也被困在这一小时。

我发现嵌套的for循环不是乱七八糟的,我可以使用内置的循环方法来大大简化我的代码。

这是我找到解释的地方:

https://github.com/Rafase282/My-FreeCodeCamp-Code/wiki/Bonfire-Where-art-thou

function where(collection, source) {
  var arr = [];
  var keys = Object.keys(source);
  // Filter array and remove the ones that do not have the keys from source.
  arr = collection.filter(function(obj) {
    //Use the Array method every() instead of a for loop to check for every key from source.
    return keys.every(function(key) {
      // Check if the object has the property and the same value.
      return obj.hasOwnProperty(key) && obj[key] === source[key];
    });
  });

  return arr;
}

答案 2 :(得分:1)

这里的一些见解具有清晰的理解和较少的循环。

一些新的javascript函数,如 some,filter,map ,对于使代码更加整洁非常方便。

function whatIsInAName(collection, source) {
  // What's in a name?
  var arr = [];
  // Only change code below this line
  collection.some(function(obj){
      var sk = Object.keys(source); //keys of source object
      var sv = Object.values(source); //values of source object
      var temp = 0; 
      for(i=0;i<sk.length;i++){ // run until the number of source properties length is reached.
        if(obj.hasOwnProperty(sk[i]) && obj[sk[i]] === sv[i]){ // if it has the same properties and value as parent object from collection 
          temp++; //temp value is increased to track if it has matched all the properties in an object
        }
      }
      if(sk.length === temp){ //if the number of iteration has matched the temp value 
        arr.push(obj);
        temp = 0; // make temp zero so as to count for the another object from collection
      }
  })
  // Only change code above this line
  return arr;
}

答案 3 :(得分:0)

&#13;
&#13;
var collection = [{
  first: "Romeo",
  last: "Montague"
}, {
  first: "Mercutio",
  last: null
}, {
  first: "Tybalt",
  last: "Capulet"
}];
var source = {
  last: "Capulet"
};

var collectionKeys = [];
for (var i = 0; i < collection.length; i++) {
  collectionKeys.push(Object.keys(collection[i]));
}
var sourceKeys = Object.keys(source);

//for every key pair
for (var t = 0; t < collectionKeys.length; t++) {
  //for every key in key pair
  for (var x = 0; x < collectionKeys[t].length; x++) {
    //for every key in search
    for (var y = 0; y < sourceKeys.length; y++) {
      //see if a key matches
      if (sourceKeys[y] == collectionKeys[t][x]) {
        if (collection[t][collectionKeys[t][x]] == source[sourceKeys[y]]) {
         alert(collection[t].first+ " "+collection[t].last);
        } else {
          console.log("value not found");
        }
      } else {
        console.log("key not found");
      }
    }
  }
}
&#13;
&#13;
&#13;

collection[collectionKeys[t][x]]更改为集合[t] [collectionKeys [t] [x]] .. collection[collectionKeys[t][x]]在控制台中提供undefined

答案 4 :(得分:0)

这就是我遇到的同样问题。

function whereAreYou(collection, source) {
  // What's in a name?

  // Only change code below this line

  var arr = [];
  var validObject;

// check each object
  for  (var each_object in collection ){
    validObject = true;
    for (var key in source ){
      if ( collection[each_object].hasOwnProperty(key)){
        if ( collection[each_object][key] != source[key]){ 
       // if no valid key
       validObject = false;
     } 
   } else {
    // if no valid value
     validObject = false;
   }
 }
  // otherwise, give it a green light
 if(validObject){
  arr.push(collection[each_object]);
  }   
}
return arr;

}

答案 5 :(得分:0)

function whatIsInAName(collection, source) {
  const keyCount = Object.keys(source).length;
  return collection.filter((item) => {
    return Object.entries(item).reduce((acc, [key, value], _, arr) => {
      if (keyCount > arr.length) {
        acc = false;
      } else if (keyCount === arr.length && !source[key]) {
        acc = false;
      } else if (source[key] && source[key] !== value) {
        acc = false;
      }
      return acc;
    }, true)
  })
}