亚洲在线久爱草,狠狠天天香蕉网,天天搞日日干久草,伊人亚洲日本欧美

為了賬號安全,請及時綁定郵箱和手機立即綁定
已解決430363個問題,去搜搜看,總會有你想問的

javascript對象多屬性值實現笛卡爾積

javascript對象多屬性值實現笛卡爾積

陪伴而非守候 2018-10-19 10:41:07
var obj = {'渠道': ["a", "b"], '城市': ["邯鄲市", "武漢"], 'stage': ["注冊", "階段一", "階段二", "階段三"], ‘date’: ["最近7天", "最近14天", "最近28天"]}要形成一系列數組如下['a', '武漢','注冊','最近七天']我現在的方式是把對象變成二維數組,然后實現function cartesianProductOf(obj) {  var test = obj.map(item => item);     return Array.prototype.reduce.call(test,function(a, b) {    var ret = [];         a.forEach(function(a) {         b.forEach(function(b) {         ret.push(a.concat([b]));       });     });   return ret;   }, [[]]); }console.log(cartesianProductOf(a))想問還有什么更好的方法,因為考慮到后期數據量大的問題
查看完整描述

1 回答

?
呼如林

TA貢獻1798條經驗 獲得超3個贊

要看你拿這個積中的元素來干什么,如果僅僅是每行,則其實這個問題換一個思路很好解決。
所謂笛卡爾積,其實質是全組合可能,這樣所有可能其實可以映射為一個多位二進制整數,這個整數的每個區段對應一個原組合(1維數組),這樣只要能取得一個值范圍內的數,就可以很快確定一個最后積里的一行(順序可能不嚴格了,但可以保證單獨的行肯定是在最后數組中)。

我們分析你原始的數據,

var obj = {'渠道': ["a", "b"], //可以對應1bit'城市': ["邯鄲市", "武漢"],//可以對應1bit'stage': 
["注冊", "階段一", "階段二", "階段三"],//可以對應2bit'date': ["最近7天", "最近14天", "最近28天"]//可以對應2bit,不過要過濾11}

這樣所有的可能就映射到1個6bit的整數上,且該值的最后2bit不能是11
然后可以直接從0-(2^6-1)中過濾掉最后是11的數字就是每行有效映射,可以反解析出實際元素組合。
比如0這個數字可以對應[a,"邯鄲市","注冊","最近7天"]
而63因為最后2bit是11,不符合,62則對應[b, "武漢","階段三","最近28天"]
要輸出所有的組合(每1行)也很簡單了(注意順序不一定對)

let outarr=[];
for(let i=0;i<64;i++){
    if( (i&0x3)!==3 ){
        let tmp=[];
        tmp.put(obj['渠道'][i>>5]);
        tmp.put(obj['城市'][(i>>4)&0X1]);
        tmp.put(obj['stage'][(i>>2)&0X3]);
        tmp.put(obj['date'][i&0X3]);
        outarr.put(tmp);
    }
}

這樣處理的好處是不涉及復雜的矩陣計算了,擴展性很好,效率也很高(是一個O(n)時間復雜度的算法,內存消耗也比較小,唯一不足是順序性不符合嚴格的笛卡爾積)這就要看你如何用這些數據了。


另外建議你所有的代碼都采用markdown格式處理,可以發現一些代碼中的問題的。


查看完整回答
反對 回復 2018-11-05
  • 1 回答
  • 0 關注
  • 864 瀏覽
慕課專欄
更多

添加回答

舉報

0/150
提交
取消
微信客服

購課補貼
聯系客服咨詢優惠詳情

幫助反饋 APP下載

慕課網APP
您的移動學習伙伴

公眾號

掃描二維碼
關注慕課網微信公眾號