10a8c90248264a8b26970b4473770bcc3df8515fJosh Gaoimport unittest
20a8c90248264a8b26970b4473770bcc3df8515fJosh Gaofrom ctypes import *
30a8c90248264a8b26970b4473770bcc3df8515fJosh Gao
40a8c90248264a8b26970b4473770bcc3df8515fJosh Gaoformats = "bBhHiIlLqQfd"
50a8c90248264a8b26970b4473770bcc3df8515fJosh Gao
60a8c90248264a8b26970b4473770bcc3df8515fJosh Gaoformats = c_byte, c_ubyte, c_short, c_ushort, c_int, c_uint, \
70a8c90248264a8b26970b4473770bcc3df8515fJosh Gao          c_long, c_ulonglong, c_float, c_double, c_longdouble
80a8c90248264a8b26970b4473770bcc3df8515fJosh Gao
90a8c90248264a8b26970b4473770bcc3df8515fJosh Gaoclass ArrayTestCase(unittest.TestCase):
100a8c90248264a8b26970b4473770bcc3df8515fJosh Gao    def test_simple(self):
110a8c90248264a8b26970b4473770bcc3df8515fJosh Gao        # create classes holding simple numeric types, and check
120a8c90248264a8b26970b4473770bcc3df8515fJosh Gao        # various properties.
130a8c90248264a8b26970b4473770bcc3df8515fJosh Gao
140a8c90248264a8b26970b4473770bcc3df8515fJosh Gao        init = range(15, 25)
150a8c90248264a8b26970b4473770bcc3df8515fJosh Gao
160a8c90248264a8b26970b4473770bcc3df8515fJosh Gao        for fmt in formats:
170a8c90248264a8b26970b4473770bcc3df8515fJosh Gao            alen = len(init)
180a8c90248264a8b26970b4473770bcc3df8515fJosh Gao            int_array = ARRAY(fmt, alen)
190a8c90248264a8b26970b4473770bcc3df8515fJosh Gao
200a8c90248264a8b26970b4473770bcc3df8515fJosh Gao            ia = int_array(*init)
210a8c90248264a8b26970b4473770bcc3df8515fJosh Gao            # length of instance ok?
220a8c90248264a8b26970b4473770bcc3df8515fJosh Gao            self.assertEqual(len(ia), alen)
230a8c90248264a8b26970b4473770bcc3df8515fJosh Gao
240a8c90248264a8b26970b4473770bcc3df8515fJosh Gao            # slot values ok?
250a8c90248264a8b26970b4473770bcc3df8515fJosh Gao            values = [ia[i] for i in range(len(init))]
260a8c90248264a8b26970b4473770bcc3df8515fJosh Gao            self.assertEqual(values, init)
270a8c90248264a8b26970b4473770bcc3df8515fJosh Gao
280a8c90248264a8b26970b4473770bcc3df8515fJosh Gao            # change the items
290a8c90248264a8b26970b4473770bcc3df8515fJosh Gao            from operator import setitem
300a8c90248264a8b26970b4473770bcc3df8515fJosh Gao            new_values = range(42, 42+alen)
310a8c90248264a8b26970b4473770bcc3df8515fJosh Gao            [setitem(ia, n, new_values[n]) for n in range(alen)]
320a8c90248264a8b26970b4473770bcc3df8515fJosh Gao            values = [ia[i] for i in range(len(init))]
330a8c90248264a8b26970b4473770bcc3df8515fJosh Gao            self.assertEqual(values, new_values)
340a8c90248264a8b26970b4473770bcc3df8515fJosh Gao
350a8c90248264a8b26970b4473770bcc3df8515fJosh Gao            # are the items initialized to 0?
360a8c90248264a8b26970b4473770bcc3df8515fJosh Gao            ia = int_array()
370a8c90248264a8b26970b4473770bcc3df8515fJosh Gao            values = [ia[i] for i in range(len(init))]
380a8c90248264a8b26970b4473770bcc3df8515fJosh Gao            self.assertEqual(values, [0] * len(init))
390a8c90248264a8b26970b4473770bcc3df8515fJosh Gao
400a8c90248264a8b26970b4473770bcc3df8515fJosh Gao            # Too many initializers should be caught
410a8c90248264a8b26970b4473770bcc3df8515fJosh Gao            self.assertRaises(IndexError, int_array, *range(alen*2))
420a8c90248264a8b26970b4473770bcc3df8515fJosh Gao
430a8c90248264a8b26970b4473770bcc3df8515fJosh Gao        CharArray = ARRAY(c_char, 3)
440a8c90248264a8b26970b4473770bcc3df8515fJosh Gao
450a8c90248264a8b26970b4473770bcc3df8515fJosh Gao        ca = CharArray("a", "b", "c")
460a8c90248264a8b26970b4473770bcc3df8515fJosh Gao
470a8c90248264a8b26970b4473770bcc3df8515fJosh Gao        # Should this work? It doesn't:
480a8c90248264a8b26970b4473770bcc3df8515fJosh Gao        # CharArray("abc")
490a8c90248264a8b26970b4473770bcc3df8515fJosh Gao        self.assertRaises(TypeError, CharArray, "abc")
500a8c90248264a8b26970b4473770bcc3df8515fJosh Gao
510a8c90248264a8b26970b4473770bcc3df8515fJosh Gao        self.assertEqual(ca[0], "a")
520a8c90248264a8b26970b4473770bcc3df8515fJosh Gao        self.assertEqual(ca[1], "b")
530a8c90248264a8b26970b4473770bcc3df8515fJosh Gao        self.assertEqual(ca[2], "c")
540a8c90248264a8b26970b4473770bcc3df8515fJosh Gao        self.assertEqual(ca[-3], "a")
550a8c90248264a8b26970b4473770bcc3df8515fJosh Gao        self.assertEqual(ca[-2], "b")
560a8c90248264a8b26970b4473770bcc3df8515fJosh Gao        self.assertEqual(ca[-1], "c")
570a8c90248264a8b26970b4473770bcc3df8515fJosh Gao
580a8c90248264a8b26970b4473770bcc3df8515fJosh Gao        self.assertEqual(len(ca), 3)
590a8c90248264a8b26970b4473770bcc3df8515fJosh Gao
600a8c90248264a8b26970b4473770bcc3df8515fJosh Gao        # slicing is now supported, but not extended slicing (3-argument)!
610a8c90248264a8b26970b4473770bcc3df8515fJosh Gao        from operator import getslice, delitem
620a8c90248264a8b26970b4473770bcc3df8515fJosh Gao        self.assertRaises(TypeError, getslice, ca, 0, 1, -1)
630a8c90248264a8b26970b4473770bcc3df8515fJosh Gao
640a8c90248264a8b26970b4473770bcc3df8515fJosh Gao        # cannot delete items
650a8c90248264a8b26970b4473770bcc3df8515fJosh Gao        self.assertRaises(TypeError, delitem, ca, 0)
660a8c90248264a8b26970b4473770bcc3df8515fJosh Gao
670a8c90248264a8b26970b4473770bcc3df8515fJosh Gao    def test_numeric_arrays(self):
680a8c90248264a8b26970b4473770bcc3df8515fJosh Gao
690a8c90248264a8b26970b4473770bcc3df8515fJosh Gao        alen = 5
700a8c90248264a8b26970b4473770bcc3df8515fJosh Gao
710a8c90248264a8b26970b4473770bcc3df8515fJosh Gao        numarray = ARRAY(c_int, alen)
720a8c90248264a8b26970b4473770bcc3df8515fJosh Gao
730a8c90248264a8b26970b4473770bcc3df8515fJosh Gao        na = numarray()
740a8c90248264a8b26970b4473770bcc3df8515fJosh Gao        values = [na[i] for i in range(alen)]
750a8c90248264a8b26970b4473770bcc3df8515fJosh Gao        self.assertEqual(values, [0] * alen)
760a8c90248264a8b26970b4473770bcc3df8515fJosh Gao
770a8c90248264a8b26970b4473770bcc3df8515fJosh Gao        na = numarray(*[c_int()] * alen)
780a8c90248264a8b26970b4473770bcc3df8515fJosh Gao        values = [na[i] for i in range(alen)]
790a8c90248264a8b26970b4473770bcc3df8515fJosh Gao        self.assertEqual(values, [0]*alen)
800a8c90248264a8b26970b4473770bcc3df8515fJosh Gao
810a8c90248264a8b26970b4473770bcc3df8515fJosh Gao        na = numarray(1, 2, 3, 4, 5)
820a8c90248264a8b26970b4473770bcc3df8515fJosh Gao        values = [i for i in na]
830a8c90248264a8b26970b4473770bcc3df8515fJosh Gao        self.assertEqual(values, [1, 2, 3, 4, 5])
840a8c90248264a8b26970b4473770bcc3df8515fJosh Gao
850a8c90248264a8b26970b4473770bcc3df8515fJosh Gao        na = numarray(*map(c_int, (1, 2, 3, 4, 5)))
860a8c90248264a8b26970b4473770bcc3df8515fJosh Gao        values = [i for i in na]
870a8c90248264a8b26970b4473770bcc3df8515fJosh Gao        self.assertEqual(values, [1, 2, 3, 4, 5])
880a8c90248264a8b26970b4473770bcc3df8515fJosh Gao
890a8c90248264a8b26970b4473770bcc3df8515fJosh Gao    def test_classcache(self):
900a8c90248264a8b26970b4473770bcc3df8515fJosh Gao        self.assertTrue(not ARRAY(c_int, 3) is ARRAY(c_int, 4))
910a8c90248264a8b26970b4473770bcc3df8515fJosh Gao        self.assertTrue(ARRAY(c_int, 3) is ARRAY(c_int, 3))
920a8c90248264a8b26970b4473770bcc3df8515fJosh Gao
930a8c90248264a8b26970b4473770bcc3df8515fJosh Gao    def test_from_address(self):
940a8c90248264a8b26970b4473770bcc3df8515fJosh Gao        # Failed with 0.9.8, reported by JUrner
950a8c90248264a8b26970b4473770bcc3df8515fJosh Gao        p = create_string_buffer("foo")
960a8c90248264a8b26970b4473770bcc3df8515fJosh Gao        sz = (c_char * 3).from_address(addressof(p))
970a8c90248264a8b26970b4473770bcc3df8515fJosh Gao        self.assertEqual(sz[:], "foo")
980a8c90248264a8b26970b4473770bcc3df8515fJosh Gao        self.assertEqual(sz[::], "foo")
990a8c90248264a8b26970b4473770bcc3df8515fJosh Gao        self.assertEqual(sz[::-1], "oof")
1000a8c90248264a8b26970b4473770bcc3df8515fJosh Gao        self.assertEqual(sz[::3], "f")
1010a8c90248264a8b26970b4473770bcc3df8515fJosh Gao        self.assertEqual(sz[1:4:2], "o")
1020a8c90248264a8b26970b4473770bcc3df8515fJosh Gao        self.assertEqual(sz.value, "foo")
1030a8c90248264a8b26970b4473770bcc3df8515fJosh Gao
1040a8c90248264a8b26970b4473770bcc3df8515fJosh Gao    try:
1050a8c90248264a8b26970b4473770bcc3df8515fJosh Gao        create_unicode_buffer
1060a8c90248264a8b26970b4473770bcc3df8515fJosh Gao    except NameError:
1070a8c90248264a8b26970b4473770bcc3df8515fJosh Gao        pass
1080a8c90248264a8b26970b4473770bcc3df8515fJosh Gao    else:
1090a8c90248264a8b26970b4473770bcc3df8515fJosh Gao        def test_from_addressW(self):
1100a8c90248264a8b26970b4473770bcc3df8515fJosh Gao            p = create_unicode_buffer("foo")
1110a8c90248264a8b26970b4473770bcc3df8515fJosh Gao            sz = (c_wchar * 3).from_address(addressof(p))
1120a8c90248264a8b26970b4473770bcc3df8515fJosh Gao            self.assertEqual(sz[:], "foo")
1130a8c90248264a8b26970b4473770bcc3df8515fJosh Gao            self.assertEqual(sz[::], "foo")
1140a8c90248264a8b26970b4473770bcc3df8515fJosh Gao            self.assertEqual(sz[::-1], "oof")
1150a8c90248264a8b26970b4473770bcc3df8515fJosh Gao            self.assertEqual(sz[::3], "f")
1160a8c90248264a8b26970b4473770bcc3df8515fJosh Gao            self.assertEqual(sz[1:4:2], "o")
1170a8c90248264a8b26970b4473770bcc3df8515fJosh Gao            self.assertEqual(sz.value, "foo")
1180a8c90248264a8b26970b4473770bcc3df8515fJosh Gao
1190a8c90248264a8b26970b4473770bcc3df8515fJosh Gao    def test_cache(self):
1200a8c90248264a8b26970b4473770bcc3df8515fJosh Gao        # Array types are cached internally in the _ctypes extension,
1210a8c90248264a8b26970b4473770bcc3df8515fJosh Gao        # in a WeakValueDictionary.  Make sure the array type is
1220a8c90248264a8b26970b4473770bcc3df8515fJosh Gao        # removed from the cache when the itemtype goes away.  This
1230a8c90248264a8b26970b4473770bcc3df8515fJosh Gao        # test will not fail, but will show a leak in the testsuite.
1240a8c90248264a8b26970b4473770bcc3df8515fJosh Gao
1250a8c90248264a8b26970b4473770bcc3df8515fJosh Gao        # Create a new type:
1260a8c90248264a8b26970b4473770bcc3df8515fJosh Gao        class my_int(c_int):
1270a8c90248264a8b26970b4473770bcc3df8515fJosh Gao            pass
1280a8c90248264a8b26970b4473770bcc3df8515fJosh Gao        # Create a new array type based on it:
1290a8c90248264a8b26970b4473770bcc3df8515fJosh Gao        t1 = my_int * 1
1300a8c90248264a8b26970b4473770bcc3df8515fJosh Gao        t2 = my_int * 1
1310a8c90248264a8b26970b4473770bcc3df8515fJosh Gao        self.assertTrue(t1 is t2)
1320a8c90248264a8b26970b4473770bcc3df8515fJosh Gao
1330a8c90248264a8b26970b4473770bcc3df8515fJosh Gaoif __name__ == '__main__':
1340a8c90248264a8b26970b4473770bcc3df8515fJosh Gao    unittest.main()
135