~ubuntu-branches/ubuntu/feisty/python-numpy/feisty

« back to all changes in this revision

Viewing changes to numpy/testing/utils.py

  • Committer: Bazaar Package Importer
  • Author(s): Matthias Klose
  • Date: 2006-07-12 10:00:24 UTC
  • Revision ID: james.westby@ubuntu.com-20060712100024-5lw9q2yczlisqcrt
Tags: upstream-0.9.8
ImportĀ upstreamĀ versionĀ 0.9.8

Show diffs side-by-side

added added

removed removed

Lines of Context:
 
1
"""
 
2
Utility function to facilitate testing.
 
3
"""
 
4
 
 
5
import os
 
6
import sys
 
7
 
 
8
__all__ = ['assert_equal', 'assert_almost_equal','assert_approx_equal',
 
9
           'assert_array_equal', 'assert_array_less',
 
10
           'assert_array_almost_equal', 'jiffies', 'memusage', 'rand',
 
11
           'runstring']
 
12
 
 
13
def rand(*args):
 
14
    """Returns an array of random numbers with the given shape.
 
15
 
 
16
    This only uses the standard library, so it is useful for testing purposes.
 
17
    """
 
18
    import random
 
19
    from numpy.core import zeros, Float64
 
20
    results = zeros(args,Float64)
 
21
    f = results.flat
 
22
    for i in range(len(f)):
 
23
        f[i] = random.random()
 
24
    return results
 
25
 
 
26
if sys.platform[:5]=='linux':
 
27
    def jiffies(_proc_pid_stat = '/proc/%s/stat'%(os.getpid()),
 
28
                _load_time=[]):
 
29
        """ Return number of jiffies (1/100ths of a second) that this
 
30
    process has been scheduled in user mode. See man 5 proc. """
 
31
        import time
 
32
        if not _load_time:
 
33
            _load_time.append(time.time())
 
34
        try:
 
35
            f=open(_proc_pid_stat,'r')
 
36
            l = f.readline().split(' ')
 
37
            f.close()
 
38
            return int(l[13])
 
39
        except:
 
40
            return int(100*(time.time()-_load_time[0]))
 
41
 
 
42
    def memusage(_proc_pid_stat = '/proc/%s/stat'%(os.getpid())):
 
43
        """ Return virtual memory size in bytes of the running python.
 
44
        """
 
45
        try:
 
46
            f=open(_proc_pid_stat,'r')
 
47
            l = f.readline().split(' ')
 
48
            f.close()
 
49
            return int(l[22])
 
50
        except:
 
51
            return
 
52
else:
 
53
    # os.getpid is not in all platforms available.
 
54
    # Using time is safe but inaccurate, especially when process
 
55
    # was suspended or sleeping.
 
56
    def jiffies(_load_time=[]):
 
57
        """ Return number of jiffies (1/100ths of a second) that this
 
58
    process has been scheduled in user mode. [Emulation with time.time]. """
 
59
        import time
 
60
        if not _load_time:
 
61
            _load_time.append(time.time())
 
62
        return int(100*(time.time()-_load_time[0]))
 
63
    def memusage():
 
64
        """ Return memory usage of running python. [Not implemented]"""
 
65
        return
 
66
 
 
67
if os.name=='nt' and sys.version[:3] > '2.3':
 
68
    # Code stolen from enthought/debug/memusage.py
 
69
    import win32pdh
 
70
    # from win32pdhutil, part of the win32all package
 
71
    def GetPerformanceAttributes(object, counter, instance = None,
 
72
                                 inum=-1, format = win32pdh.PDH_FMT_LONG, machine=None):
 
73
        # NOTE: Many counters require 2 samples to give accurate results,
 
74
        # including "% Processor Time" (as by definition, at any instant, a
 
75
        # thread's CPU usage is either 0 or 100).  To read counters like this,
 
76
        # you should copy this function, but keep the counter open, and call
 
77
        # CollectQueryData() each time you need to know.
 
78
        # See http://msdn.microsoft.com/library/en-us/dnperfmo/html/perfmonpt2.asp
 
79
        # My older explanation for this was that the "AddCounter" process forced
 
80
        # the CPU to 100%, but the above makes more sense :)
 
81
        path = win32pdh.MakeCounterPath( (machine,object,instance, None, inum,counter) )
 
82
        hq = win32pdh.OpenQuery()
 
83
        try:
 
84
            hc = win32pdh.AddCounter(hq, path)
 
85
            try:
 
86
                win32pdh.CollectQueryData(hq)
 
87
                type, val = win32pdh.GetFormattedCounterValue(hc, format)
 
88
                return val
 
89
            finally:
 
90
                win32pdh.RemoveCounter(hc)
 
91
        finally:
 
92
            win32pdh.CloseQuery(hq)
 
93
 
 
94
    def memusage(processName="python", instance=0):
 
95
        return GetPerformanceAttributes("Process", "Virtual Bytes",
 
96
                                        processName, instance,
 
97
                                        win32pdh.PDH_FMT_LONG, None)
 
98
 
 
99
def assert_equal(actual,desired,err_msg='',verbose=1):
 
100
    """ Raise an assertion if two items are not
 
101
        equal.  I think this should be part of unittest.py
 
102
    """
 
103
    if isinstance(desired, dict):
 
104
        assert isinstance(actual, dict),`type(actual)`
 
105
        assert_equal(len(actual),len(desired),err_msg,verbose)
 
106
        for k,i in desired.items():
 
107
            assert actual.has_key(k),`k`
 
108
            assert_equal(actual[k], desired[k], 'key=%r\n%s' % (k,err_msg), verbose)
 
109
        return
 
110
    if isinstance(desired, list) and isinstance(actual, list):
 
111
        assert_equal(len(actual),len(desired),err_msg,verbose)
 
112
        for k in range(len(desired)):
 
113
            assert_equal(actual[k], desired[k], 'item=%r\n%s' % (k,err_msg), verbose)
 
114
        return
 
115
    from numpy.core import ArrayType
 
116
    if isinstance(actual, ArrayType) or isinstance(desired, ArrayType):
 
117
        return assert_array_equal(actual, desired, err_msg)
 
118
    msg = '\nItems are not equal:\n' + err_msg
 
119
    try:
 
120
        if ( verbose and len(repr(desired)) < 100 and len(repr(actual)) ):
 
121
            msg =  msg \
 
122
                 + 'DESIRED: ' + repr(desired) \
 
123
                 + '\n ACTUAL: ' + repr(actual)
 
124
    except:
 
125
        msg =  msg \
 
126
             + 'DESIRED: ' + repr(desired) \
 
127
             + '\n ACTUAL: ' + repr(actual)
 
128
    assert desired == actual, msg
 
129
    return
 
130
 
 
131
def assert_almost_equal(actual,desired,decimal=7,err_msg='',verbose=1):
 
132
    """ Raise an assertion if two items are not
 
133
        equal.  I think this should be part of unittest.py
 
134
    """
 
135
    from numpy.core import ArrayType
 
136
    if isinstance(actual, ArrayType) or isinstance(desired, ArrayType):
 
137
        return assert_array_almost_equal(actual, desired, decimal, err_msg)
 
138
    msg = '\nItems are not equal:\n' + err_msg
 
139
    try:
 
140
        if ( verbose and len(repr(desired)) < 100 and len(repr(actual)) ):
 
141
            msg =  msg \
 
142
                 + 'DESIRED: ' + repr(desired) \
 
143
                 + '\n ACTUAL: ' + repr(actual)
 
144
    except:
 
145
        msg =  msg \
 
146
             + 'DESIRED: ' + repr(desired) \
 
147
             + '\n ACTUAL: ' + repr(actual)
 
148
    assert round(abs(desired - actual),decimal) == 0, msg
 
149
 
 
150
 
 
151
def assert_approx_equal(actual,desired,significant=7,err_msg='',verbose=1):
 
152
    """ Raise an assertion if two items are not
 
153
        equal.  I think this should be part of unittest.py
 
154
        Approximately equal is defined as the number of significant digits
 
155
        correct
 
156
    """
 
157
    import math
 
158
    msg = '\nItems are not equal to %d significant digits:\n' % significant
 
159
    msg += err_msg
 
160
    actual, desired = map(float, (actual, desired))
 
161
    if desired==actual:
 
162
        return
 
163
    # Normalized the numbers to be in range (-10.0,10.0)
 
164
    scale = float(pow(10,math.floor(math.log10(0.5*(abs(desired)+abs(actual))))))
 
165
    try:
 
166
        sc_desired = desired/scale
 
167
    except ZeroDivisionError:
 
168
        sc_desired = 0.0
 
169
    try:
 
170
        sc_actual = actual/scale
 
171
    except ZeroDivisionError:
 
172
        sc_actual = 0.0
 
173
    try:
 
174
        if ( verbose and len(repr(desired)) < 100 and len(repr(actual)) ):
 
175
            msg =  msg \
 
176
                 + 'DESIRED: ' + repr(desired) \
 
177
                 + '\n ACTUAL: ' + repr(actual)
 
178
    except:
 
179
        msg =  msg \
 
180
             + 'DESIRED: ' + repr(desired) \
 
181
             + '\n ACTUAL: ' + repr(actual)
 
182
    assert math.fabs(sc_desired - sc_actual) < pow(10.,-1*significant), msg
 
183
 
 
184
 
 
185
def assert_array_equal(x,y,err_msg=''):
 
186
    from numpy.core import asarray, alltrue, equal, shape, ravel, array2string
 
187
    x,y = asarray(x), asarray(y)
 
188
    msg = '\nArrays are not equal'
 
189
    try:
 
190
        assert 0 in [len(shape(x)),len(shape(y))] \
 
191
               or (len(shape(x))==len(shape(y)) and \
 
192
                   alltrue(equal(shape(x),shape(y)))),\
 
193
                   msg + ' (shapes %s, %s mismatch):\n\t' \
 
194
                   % (shape(x),shape(y)) + err_msg
 
195
        reduced = ravel(equal(x,y))
 
196
        cond = alltrue(reduced)
 
197
        if not cond:
 
198
            s1 = array2string(x,precision=16)
 
199
            s2 = array2string(y,precision=16)
 
200
            if len(s1)>120: s1 = s1[:120] + '...'
 
201
            if len(s2)>120: s2 = s2[:120] + '...'
 
202
            match = 100-100.0*reduced.tolist().count(1)/len(reduced)
 
203
            msg = msg + ' (mismatch %s%%):\n\tArray 1: %s\n\tArray 2: %s' % (match,s1,s2)
 
204
        assert cond,\
 
205
               msg + '\n\t' + err_msg
 
206
    except ValueError:
 
207
        raise ValueError, msg
 
208
 
 
209
 
 
210
def assert_array_almost_equal(x,y,decimal=6,err_msg=''):
 
211
    from numpy.core import asarray, alltrue, equal, shape, ravel,\
 
212
         array2string, less_equal, around
 
213
    x = asarray(x)
 
214
    y = asarray(y)
 
215
    msg = '\nArrays are not almost equal'
 
216
    try:
 
217
        cond = alltrue(equal(shape(x),shape(y)))
 
218
        if not cond:
 
219
            msg = msg + ' (shapes mismatch):\n\t'\
 
220
                  'Shape of array 1: %s\n\tShape of array 2: %s' % (shape(x),shape(y))
 
221
        assert cond, msg + '\n\t' + err_msg
 
222
        reduced = ravel(equal(less_equal(around(abs(x-y),decimal),10.0**(-decimal)),1))
 
223
        cond = alltrue(reduced)
 
224
        if not cond:
 
225
            s1 = array2string(x,precision=decimal+1)
 
226
            s2 = array2string(y,precision=decimal+1)
 
227
            if len(s1)>120: s1 = s1[:120] + '...'
 
228
            if len(s2)>120: s2 = s2[:120] + '...'
 
229
            match = 100-100.0*reduced.tolist().count(1)/len(reduced)
 
230
            msg = msg + ' (mismatch %s%%):\n\tArray 1: %s\n\tArray 2: %s' % (match,s1,s2)
 
231
        assert cond,\
 
232
               msg + '\n\t' + err_msg
 
233
    except ValueError:
 
234
        print sys.exc_value
 
235
        print shape(x),shape(y)
 
236
        print x, y
 
237
        raise ValueError, 'arrays are not almost equal'
 
238
 
 
239
def assert_array_less(x,y,err_msg=''):
 
240
    from numpy.core import asarray, alltrue, less, equal, shape, ravel, array2string
 
241
    x,y = asarray(x), asarray(y)
 
242
    msg = '\nArrays are not less-ordered'
 
243
    try:
 
244
        assert alltrue(equal(shape(x),shape(y))),\
 
245
               msg + ' (shapes mismatch):\n\t' + err_msg
 
246
        reduced = ravel(less(x,y))
 
247
        cond = alltrue(reduced)
 
248
        if not cond:
 
249
            s1 = array2string(x,precision=16)
 
250
            s2 = array2string(y,precision=16)
 
251
            if len(s1)>120: s1 = s1[:120] + '...'
 
252
            if len(s2)>120: s2 = s2[:120] + '...'
 
253
            match = 100-100.0*reduced.tolist().count(1)/len(reduced)
 
254
            msg = msg + ' (mismatch %s%%):\n\tArray 1: %s\n\tArray 2: %s' % (match,s1,s2)
 
255
        assert cond,\
 
256
               msg + '\n\t' + err_msg
 
257
    except ValueError:
 
258
        print shape(x),shape(y)
 
259
        raise ValueError, 'arrays are not less-ordered'
 
260
 
 
261
def runstring(astr, dict):
 
262
    exec astr in dict