<div dir="ltr"><div><div><div><div><div>Oops, looks like I accidentally pasted the test_naivearr2.py twice!  Egad!  Sorry! <br><br></div>The test should end after <br><br></div>if __name__ == &quot;__main__&quot;:<br></div>    unittest.main()<br><br></div>So solly!<br></div>Dave<br></div><div class="gmail_extra"><br><div class="gmail_quote">On Sat, Jun 27, 2015 at 2:33 PM, David Jackson <span dir="ltr">&lt;<a href="mailto:deepbsd.ale@gmail.com" target="_blank">deepbsd.ale@gmail.com</a>&gt;</span> wrote:<br><blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex"><div dir="ltr"><div><div><div><div><div><div><div><div><div><div><div><div><div><div>Hi!<br><br></div>So I&#39;m having a little trouble in Python4.  One of the assignments is to create a 3-d array from a 2-d array, using the array module.  The array as introduced in the lesson is a list, but could be another data structure.  For this assignment, it asks for a list implementation.  Here&#39;s the 2-d array as introduced in the text.  First, the test, since we&#39;re learning agile and test-driven development:<br><br></div>*** snip of testarray.py ***<br><br>#!/usr/bin/env python3<br><br>&quot;&quot;&quot;<br>testarray.py: Test list-of-list based array implementations using tuple<br>subscripting.<br>&quot;&quot;&quot;<br><br>import unittest<br>import arr_single_list as arr<br><br>class TestArray(unittest.TestCase):<br><br>    def test_zeroes(self):<br>        for N in range(4):<br>            a = arr.array(N, N)<br>            for i in range(N):<br>                for j in range(N):<br>                    #self.assertEqual(a[i][j], 0)<br>                    self.assertEqual(a[i, j], 0)<br><br>    def test_identity(self):<br>        for N in range(4):<br>            a = arr.array(N, N)<br>            for i in range(N):<br>                #a[i][i] = 1<br>                a[i, i] = 1<br>            for i in range(N):<br>                for j in range(N):<br>                    #self.assertEqual(a[i][j], i==j) <br>                    self.assertEqual(a[i, j], i==j)<br><br>    def test_one_cell(self):<br>        N = 10 <br>        a = arr.array(N,N)<br>        a[2,3] = 1<br>        for i in range(N):<br>            for j in range(N):<br>                if i==2 and j==3:<br>                    self.assertEqual(a[i,j], 1)<br>                else:<br>                    self.assertEqual(a[i,j], 0)<br><br><br>    def _index(self, a, r, c):<br>        return a[r, c]<br><br>    def test_key_validity(self):<br>        a = arr.array(10, 10)<br>        self.assertRaises(KeyError, self._index, a, -1, 1)<br>        self.assertRaises(KeyError, self._index, a, 10, 1)<br>        self.assertRaises(KeyError, self._index, a, 1, -1)<br>        self.assertRaises(KeyError, self._index, a, 1, 10)<br><br><br>if __name__ == &quot;__main__&quot;:<br>    unittest.main()<br><br></div>*** end snip of test_array.py ***<br><br></div>Here&#39;s the 2-D array called called arr_single_list.py:<br><br></div>*** start snip of arr_single_list.py  ***<br>#!/usr/bin/env python3<br><br>&quot;&quot;&quot;<br>arr_single_list.py:  Class-based single-list allowing tuple subscripting.<br>&quot;&quot;&quot;<br><br>class array:<br><br>    def __init__(self, M, N):<br>        &quot;Create a list long enough to hold M*N elements.&quot;<br>        self._data = [0] * M * N<br>        self._rows = M<br>        self._cols = N<br><br><br>    def __getitem__(self, key):<br>        &quot;Returns the appropriate element for a two-element subscript tuple.&quot;<br>        row, col = self._validate_key(key)<br>        return self._data[row*self._cols+col]<br><br>    def __setitem__(self, key, value):<br>        &quot;Sets the appropriate element for a two-element subscript tuple.&quot;<br>        row, col = self._validate_key(key)<br>        self._data[row*self._cols+col] = value<br><br>    def _validate_key(self, key):<br>        &#39;&#39;&#39;<br>        Validates a key against the array&#39;s shape, returning good tuples. <br>        Raises KeyError on problems.<br>        &#39;&#39;&#39;<br>        row, col = key<br>        if (0 &lt;= row &lt; self._rows and 0 &lt;= col &lt; self._cols):<br>            return key<br>        raise KeyError(&quot;subscript out of range&quot;)<br><br></div>***  end snip of arr_single_list.py ***<br><br></div>Okay, this all seems pretty simple, and it ran just fine through the tests.  The __{get|set}item__ methods <br>seem to be row oriented and simply take successive rows and stick them each onto the end of the list.<br></div>Fine.  So a third dimension, would, I should think, be fairly simple, but I seem to have missed something. <br><br></div><div>Here&#39;s my file, called naivearr2.py:<br><br></div><div>*** start snip of naivearr2.py  ***<br>#!/usr/bin/env python3<br><br>&quot;&quot;&quot;<br>naievearr2.py:  Naive implementation of 3-D array using lists and tuple<br>subscripts<br>&quot;&quot;&quot;<br><br>import array as sys_array<br><br>class array:<br><br>    def __init__(self, M, N, O):<br>        &quot;Create 3-D array of lists&quot;<br>        self._data = sys_array.array(&quot;i&quot;, [0] * M * N * O)<br>        self._rows = M<br>        self._cols = N<br>        self._depth = O<br><br>    def __getitem__(self, key):<br>        &quot;returns the appropriate element for a three-element subscript tuple.&quot;<br>        row, col, depth = self._validate_key(key)<br>        return self._data[row*self._cols+col*self._depth+depth]<br><br>    def __setitem__(self, key, value):<br>        &quot;sets the appropriate element for a three-element subscript tuble.&quot;<br>        row, col, depth = self._validate_key(key)<br>        self._data[row*self._cols+col*self._depth+depth] = value<br><br>    def _validate_key(self, key):<br>        &quot;&quot;&quot;Validates a key against the array&#39;s shape, returning good tuples.<br>        Raises KeyError on problems.&quot;&quot;&quot;<br>        row, col, depth = key<br>        if (0 &lt;= row &lt; self._rows and 0 &lt;= col &lt; self._cols and 0 &lt;= depth &lt; self._depth):<br>            return key<br>        raise KeyError(&quot;subscript out of range&quot;)<br><br></div><div>*** end snip of naivearr2.py ***<br><br><br></div><div>I thought for sure this would work, but there&#39;s a gotcha in there somewhere.  Sure enough, the <br></div><div>__setitem__ sets the correct cells to &#39;1&#39; when in the code below, but I get extras set to one as well:<br><br><br></div><div>*** start snip of test_naivearr2.py ***<br></div><div>import unittest<br>import naivearr2 as arr<br><br><br>class TestArray(unittest.TestCase):<br>    def test_zeroes(self):<br>        for N in range(6):<br>            a = arr.array(N, N, N)<br>            for i in range(N):<br>                for j in range(N):<br>                    for k in range(N):<br>                        #print(&quot;N={}, i={}, j={}, k={}&quot;.format(N, i, j, k))<br>                        self.assertEqual(a[i, j, k], 0)<br><br>    def test_identity(self):<br>        for N in range(6):<br>            a = arr.array(N, N, N)<br>            for i in range(N):<br>                a[i, i, i] = 1<br>                print(&quot;a[{},{},{}] &quot;.format(i, i, i))<br>            for i in range(N):<br>                for j in range(N):<br>                    for k in range(N):<br>                        if i==j==k:<br>                            #print(&quot;***A[{},{},{}]&quot;.format(i, j, k))<br>                            self.assertEqual(a[i, j, k], 1)<br>                        if not i==j==k and a[i,j,k] == 1:<br>                            print(&quot;Dammit!  A[{},{},{}] == 1&quot;.format(i, j, k))<br>                            #self.assertEqual(a[i,j,k], 0)<br><br>    def _index(self, a, r, c, d):<br>        return a[r, c, d]<br><br>    def test_key_validity(self):<br>        a = arr.array(10, 10, 10)<br>        self.assertRaises(KeyError, self._index, a, -1, 1, 1)<br>        self.assertRaises(KeyError, self._index, a, 10, 1, 10)<br>        self.assertRaises(KeyError, self._index, a, 1, -1, -10)<br>        self.assertRaises(KeyError, self._index, a, 1, 10, -1)<br><br><br><br>if __name__ == &quot;__main__&quot;:<br>    unittest.main()<br>import unittest<br>import naivearr2 as arr<br><br><br>class TestArray(unittest.TestCase):<br>    def test_zeroes(self):<br>        for N in range(6):<br>            a = arr.array(N, N, N)<br>            for i in range(N):<br>                for j in range(N):<br>                    for k in range(N):<br>                        #print(&quot;N={}, i={}, j={}, k={}&quot;.format(N, i, j, k))<br>                        self.assertEqual(a[i, j, k], 0)<br><br>    def test_identity(self):<br>        for N in range(6):<br>            a = arr.array(N, N, N)<br>            for i in range(N):<br>                a[i, i, i] = 1<br>                print(&quot;a[{},{},{}] &quot;.format(i, i, i))<br>            for i in range(N):<br>                for j in range(N):<br>                    for k in range(N):<br>                        if i==j==k:<br>                            #print(&quot;***A[{},{},{}]&quot;.format(i, j, k))<br>                            self.assertEqual(a[i, j, k], 1)<br>                        if not i==j==k and a[i,j,k] == 1:<br>                            print(&quot;Dammit!  A[{},{},{}] == 1&quot;.format(i, j, k))<br>                            #self.assertEqual(a[i,j,k], 0)<br><br>    def _index(self, a, r, c, d):<br>        return a[r, c, d]<br><br>    def test_key_validity(self):<br>        a = arr.array(10, 10, 10)<br>        self.assertRaises(KeyError, self._index, a, -1, 1, 1)<br>        self.assertRaises(KeyError, self._index, a, 10, 1, 10)<br>        self.assertRaises(KeyError, self._index, a, 1, -1, -10)<br>        self.assertRaises(KeyError, self._index, a, 1, 10, -1)<br><br><br><br>if __name__ == &quot;__main__&quot;:<br>    unittest.main()<br><br></div><div>*** end snip of test_naivearr2.py ***<br><br></div><div>Everything passes except test_identity.   Sure enough, a[0,0,0] = 1, a[1,1,1]=1, etc,<br></div><div>but I also get <br></div><div>A[0,2,1] == 1<br></div><div>A[0,4,2] == 1<br></div><div>A[1,3,2] == 1<br></div><div>A[2,0,4] == 1<br></div><div>A[2,4,3] == 1<br></div><div>A[3,1,2] == 1<br></div><div>A[4,0,2] == 1<br></div><div>A[4,2,3] == 1<br></div><br><br></div>So I guess my __setitem__ is goofy.  Or I guess I could be calling a value with<br></div>__getitem__ that is the wrong value.  <br><br></div>Can anyone see what I&#39;m doing wrong?  <br><br></div>Any help is appreciated, and thanks in advance!<br><br></div>Dave<br><div><div><div><div><div><div><br></div><div><br><br><br><br><br><br><div><div><div><br><br><br><br><br><br><div><div><br><br><br><br><div><br><br><br></div></div></div></div></div></div></div></div></div></div></div></div></div>
</blockquote></div><br></div>