2017-09-06 18 views
0

の配列私はこの1つのようなコードを持っている:モカ、配列と範囲

let Foo = class Foo { 
    constructor(a) { 
     this.a = a.slice(); 
    } 

    bar() { 
     this.set(0, 1, [1]); 
     this.set(1, 1, [1]); 
    } 

    set(x, y, n) { 
     this.a[x][y] = n; 
    } 

    get() { 
     return this.a; 
    } 
}; 

module.exports = Foo; 

だから、プロパティwhisは、配列の配列、それを変更set機能、およびsetを使用する機能ですとゲッター。私が最初にsource変数を宣言し

const Foo = require('./../foo.js'), 
    source = [[1, 2, 3], [4, 5, 6]], 
    chai = require('chai'), 
    expect = chai.expect; 

describe('Foo',() => { 
    describe('bar',() => { 
     it('expect to modify the array',() => { 
      let foo = new Foo(source); 

      foo.bar(); 

      expect(foo.a).to.deep.equal([[1, [1], 3], [4, [1], 6]]); 
     }); 
    }); 

    describe('get',() => { 
     it('expect to return the array',() => { 
      let foo = new Foo(source); 
      expect(foo.get()).to.deep.equal([1, 2, 3]); 
     }); 
    }); 
}); 

これで、新しいFoo各テストを構築するためにそれを使用する:

は今、私はモカと、ユニットテストを書きます。

しかし、結果はbarテストgetテストでfooのプロパティを変更すること...です:

Foo 
    bar 
     ✓ expect to modify the array 
    get 
     1) expect to return the array 


    1 passing (19ms) 
    1 failing 

    1) Foo get expect to return the array: 

     AssertionError: expected [ [ 1, [ 1 ], 3 ], [ 4, [ 1 ], 6 ] ] to deeply equal [ 1, 2, 3 ] 
     + expected - actual 

     [ 
     - [ 
     - 1 
     - [ 
     -  1 
     - ] 
     - 3 
     - ] 
     - [ 
     - 4 
     - [ 
     -  1 
     - ] 
     - 6 
     - ] 
     + 1 
     + 2 
     + 3 
     ] 

     at Proxy.assertEqual (node_modules/chai/lib/chai/core/assertions.js:1020:19) 
     at Proxy.methodWrapper (node_modules/chai/lib/chai/utils/addMethod.js:57:25) 
     at Context.it (test/foo.js:20:30) 

モカテストに匿名関数の代わりに、矢印機能を使用すると、何も変更はありません、spliceを使用してソースを値でコピーすることもできます。

私は何かを忘れましたか?どういうわけか、私は何とか両方のプロパティーの同じ参照を同じ配列に帰していることは明らかですが、私はどのように、そしてもっと重要なのか、私は別々に、fooを作成する方法を理解することができません。

+0

@Jonasw実際のコードでは、チェックが、それはtが:)失敗doesnのを保証するために作られています – DrakaSAN

答えて

1

this.a = a.slice()は浅いコピーしか取らないからです。しかし、aはネストされた配列なので、ネストされた配列内の何かを変更すると、this.asourceの両方に表示されます。

あなたが変更することができます:

this.a = a.slice(); 

に:あなたが初期化されたものsourceと比較されていないので、2番目のテストは、どのような方法を変更する必要があります

this.a = (function deepSlice(a) { 
    return Array.isArray(a) ? a.map(deepSlice) : a; 
})(a); 

注意。だから、変更:

expect(foo.get()).to.deep.equal([1, 2, 3]); 

へ:

expect(foo.get()).to.deep.equal([[1, 2, 3], [4, 5, 6]]); 
+0

簡単な 'a.mapで試してみました((B)= > {戻りb.slice()}) '、しかし、それは働いていなかったと私は間違った方向に行っていたと思った、深く住んでいた必要があります – DrakaSAN

+0

これはあなたの問題を解決しましたか? – trincot

+1

はい、モバイルアプリは緑色のマークを送信していません:) – DrakaSAN