最新消息:雨落星辰是一个专注网站SEO优化、网站SEO诊断、搜索引擎研究、网络营销推广、网站策划运营及站长类的自媒体原创博客

jQueryJavascript index into collectionmap by object property? - Stack Overflow

programmeradmin0浏览0评论

I have the following Javascript defining an array of countries and their states...

var countryStateMap = [{"CountryCode":"CA","Name":"Canada","States":[{"StateCode":"S!","CountryCode":"CA","Name":"State 1"},{"StateCode":"S2","CountryCode":"CA","Name":"State 2"}]},"CountryCode":"US","Name":"United States","States":[{"StateCode":"S1","CountryCode":"US","Name":"State 1"}]}];

Based on what country the user selects, I need to refresh a select box's options for states from the selected Country object. I know I can index into the country collection with an int index like so...

countryStateMap[0].States

I need a way to get the Country by CountryCode property though. I know the following doesn't work but what I would like to do is something like this...

countryStateMap[CountryCode='CA'].States

Can this be achieved without pletely rebuilding my collection's structure or iterating over the set each time to find the one I want?

UPDATE: I accepted mVChr's answer because it worked and was the simplest solution even though it required a second map.

The solution we actually ended up going with was just using the country select box's index to index into the collection. This worked because our country dropdown was also being populated from our data structure. Here is how we indexed in...

countryStateMap[$('#country').attr("selectedIndex")]

If you need to do it any other way, use any of the below solutions.

I have the following Javascript defining an array of countries and their states...

var countryStateMap = [{"CountryCode":"CA","Name":"Canada","States":[{"StateCode":"S!","CountryCode":"CA","Name":"State 1"},{"StateCode":"S2","CountryCode":"CA","Name":"State 2"}]},"CountryCode":"US","Name":"United States","States":[{"StateCode":"S1","CountryCode":"US","Name":"State 1"}]}];

Based on what country the user selects, I need to refresh a select box's options for states from the selected Country object. I know I can index into the country collection with an int index like so...

countryStateMap[0].States

I need a way to get the Country by CountryCode property though. I know the following doesn't work but what I would like to do is something like this...

countryStateMap[CountryCode='CA'].States

Can this be achieved without pletely rebuilding my collection's structure or iterating over the set each time to find the one I want?

UPDATE: I accepted mVChr's answer because it worked and was the simplest solution even though it required a second map.

The solution we actually ended up going with was just using the country select box's index to index into the collection. This worked because our country dropdown was also being populated from our data structure. Here is how we indexed in...

countryStateMap[$('#country').attr("selectedIndex")]

If you need to do it any other way, use any of the below solutions.

Share Improve this question edited May 9, 2011 at 20:59 Jesse Webb asked May 9, 2011 at 20:05 Jesse WebbJesse Webb 45.3k31 gold badges108 silver badges146 bronze badges 1
  • For the most efficient solution you have to change your structure (from array to object). – Felix Kling Commented May 9, 2011 at 20:09
Add a ment  | 

3 Answers 3

Reset to default 6

One thing you could do is cache a map so you only have to do the iteration once:

var csmMap = {};
for (var i = 0, cl = countryStateMap.length; i < cl; i++) {
  csmMap[countryStateMap[i].CountryCode] = i;
}

Then if countryCode = 'CA' you can find its states like:

countryStateMap[csmMap[countryCode]].States
countryStateMap.get = function(cc) {
    if (countryStateMap.get._cache[cc] === void 0) {
        for (var i = 0, ii = countryStateMap.length; i < ii; i++) {
            if (countryStateMap[i].CountryCode === cc) {
                countryStateMap.get._cache[cc] = countryStateMap[i];
                break;
            }
        }
    }
    return countryStateMap.get._cache[cc];
}
countryStateMap.get._cache = {};

Now you can just call .get("CA") like so

countryStateMap.get("CA").States

If you prefer syntatic sugar you may be interested in underscore which has utility methods to make this kind of code easier to write

countryStateMap.get = _.memoize(function(cc) {
    return _.filter(countryStateMap, function(val) {
        val.CountryCode = cc;
    })[0];
});

_.memoize , _.filter

love your local jQuery:

small little function for you:

getByCountryCode = function(code){var res={};$.each(countryStateMap, function(i,o){if(o.CountryCode==code)res=o;return false;});return res}

so do this then:

getByCountryCode("CA").States

and it returns:

[Object, Object]

发布评论

评论列表(0)

  1. 暂无评论