使用表单参数使用Javascript搜索JSON

时间:2015-09-11 21:28:59

标签: javascript arrays angularjs search

我制作的网络应用程序将根据给定的参数搜索卡片。

问题在于卡片的类型不同。例如,一张卡片可能包含"income": 4,而另一张卡片的行为完全不同,并且具有属性"cost" : 5。我的意思是我的JSON有5种不同的对象,尽管它们有许多相似之处,但它们有一定的区别。

所以,让我们说我的用户根据标题搜索一张卡片。所有这些都有这个属性,所以很容易做出这样的条件。

if ((item.name.toLowerCase().indexOf(cardParams.searchTitle.toLowerCase())  > -1) && (cardParams.searchTitle != null ) && (cardParams
        .searchTitle.length > 0)){

但是如果我的用户想要搜索正文中的文本呢?所有这些都有一个,所以这导致另一个条件,开始让事情变得尴尬。

此外,让我的用户触发我最糟糕的情况,并询问两个属性,即没有卡同时拥有它们以及上面的那些属性。有人会说,我应该在我的表格上工作,使它们互相排斥,但从程序上来说这超出了我。

我决定采用的方法是单独搜索每个属性并将结果全部保存到数组中。如果我有一个卡的副本与许多有效属性(非空或空)一样多,那么我会保留它们。

这真的很笨拙而且不是最佳的。我确信有一些非常简单的解决方案,我无法想到。

我如何处理这样的问题?创造大量条件是唯一的出路吗?我该怎么办?

编辑:感谢您的downvotes。这就像我要求的一样。

1 个答案:

答案 0 :(得分:0)

如果要搜索javascript中的对象,可以循环访问属性,并访问object.hasOwnProperty(propertyName)返回true的对象

例如,你看到一堆具有不同属性的卡片,但搜索将遍历每张卡片的所有属性,并选择匹配的卡片,然后搜索下一张匹配的卡片。

最后它会显示结果,或者只是说没有找到结果;)

var cards = [{
  title: 'Card 1',
  prop1: 'Test of card1',
  description: 'Description of card1',
  customCard1: 'Custom property'
}, {
  title: 'Card 2',
  description: 'Description of card2',
  customCard2: 'Custom property card2'
}];

function searchCards() {
  var txt = document.getElementById('searchBox').value.toLowerCase(),
    i, len, card, prop, matches = [],
    val;

  for (i = 0, len = cards.length; i < len; i++) {
    card = cards[i];
    for (prop in card) {
      if (card.hasOwnProperty(prop)) {
        val = card[prop];
        if (typeof val !== 'undefined' && val.toLowerCase && val.toLowerCase().indexOf(txt) >= 0) {
          // this card matches
          matches.push(card);
          break;
        }
      }
    }
  }
  showMatches(matches);
}

function showMatches(matches) {
  var elem = document.getElementById('result'),
    i, len, content = '';
  if (typeof matches === 'undefined' || !matches.length) {
    elem.innerHTML = '<i>No results found</i>';
    return;
  }
  for (i = 0, len = matches.length; i < len; i++) {
    content += '<div><b>title:</b>' + matches[i].title + '</div>';
  }
  elem.innerHTML = content;
}
<input type="text" id="searchBox" />
<button type="button" onclick="javascript:searchCards()">Search</button>
<div id="result"></div>

根据评论进行更新

如果你有多个输入字段,你可以给它们一个额外的类来识别它们,然后让jQuery根据你的选择器(在我的例子中,.search)返回所有匹配的元素,并获得值由用户给出,那么您可以简单地检查您的卡是否具有已定义的值,以及该定义的值是否真的是卡本身的一部分

我重复使用了第一段代码中的一些代码,不想花太多时间在它上面;)

var cards = [{
  title: 'Card 1',
  prop1: 'Test of card1',
  description: 'Description of card1',
  customCard1: 'Custom property'
}, {
  title: 'Card 2',
  description: 'Description of card2',
  customCard2: 'Custom property card2'
}];


function getSearchParameters() {
  var properties = [];
  $('.search').each(function() {
    if (this.value) {
      properties.push(this.value);
    }
  });
  return properties;
}

function search() {
  var properties = getSearchParameters(), i, len, card, matches = [], p, plen, prop, match;
  for (i = 0, len = cards.length; i < len; i++) {
    card = cards[i];
    match = true;
    for (p = 0, plen = properties.length; p < plen; p++) {
      prop = properties[p];
      if (typeof card[prop] === 'undefined' || !card.hasOwnProperty(prop) ) {
        // didn't find a property, this doesn't match
        match = false;
        break;
      }
    }
    if (match) {
      matches.push(card);
    }
  }
  showMatches(matches);
}


function showMatches(matches) {
  var elem = document.getElementById('result'),
    i, len, content = '';
  if (typeof matches === 'undefined' || !matches.length) {
    elem.innerHTML = '<i>No results found</i>';
    return;
  }
  for (i = 0, len = matches.length; i < len; i++) {
    content += '<div><b>title:</b>' + matches[i].title + '</div>';
  }
  elem.innerHTML = content;
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<input type="text" class="search" />
<input type="text" class="search" />
<input type="text" class="search" />
<input type="text" class="search" />
<input type="text" class="search" />
<input type="text" class="search" />
<input type="text" class="search" />
<input type="text" class="search" />
<button type="button" onclick="search()">Search for matching properties</button>
<div id="result">
</div>