test_seq_pool.py 7.0 KB
Newer Older
1
#   Copyright (c) 2018 PaddlePaddle Authors. All Rights Reserved.
D
dzhwinter 已提交
2
#
D
dzhwinter 已提交
3 4 5
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
# You may obtain a copy of the License at
D
dzhwinter 已提交
6
#
D
dzhwinter 已提交
7
#     http://www.apache.org/licenses/LICENSE-2.0
D
dzhwinter 已提交
8
#
D
dzhwinter 已提交
9 10 11 12 13 14
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS,
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
# See the License for the specific language governing permissions and
# limitations under the License.

15 16
import unittest
import numpy as np
17
from .op_test import OpTest
18 19


20
class TestSeqAvgPool(OpTest):
21 22 23 24 25 26 27
    def convert_to_offset(self, lod):
        offset = [[0] for i in lod]
        for i, level in enumerate(lod):
            for seq_len in level:
                offset[i].append(offset[i][-1] + seq_len)
        return offset

28 29
    def set_data(self):
        self.op_type = 'sequence_pool'
30
        # one level, batch size is 4
31
        x = np.random.uniform(0.1, 1, [11, 23]).astype('float32')
32
        lod = [[4, 1, 3, 3]]
33
        self.inputs = {'X': (x, lod)}
34
        offset = self.convert_to_offset(lod)
35

36
        out = np.zeros((4, 23)).astype('float32')
37
        self.outputs = {'Out': out}
38
        return x, offset, out
39

40
    def compute(self, x, offset, out):
D
dzhwinter 已提交
41
        self.attrs = {'pooltype': "AVERAGE"}
42 43
        for i in range(len(offset[0]) - 1):
            sub_x = x[offset[0][i]:offset[0][i + 1], :]
44 45
            out[i] = sub_x.mean(axis=0)

46
    def setUp(self):
47 48
        x, offset, out = self.set_data()
        self.compute(x, offset, out)
49 50 51 52 53

    def test_check_output(self):
        self.check_output()

    def test_check_grad(self):
54 55 56
        # Remove MaxIndex after check_grad is refined.
        self.outputs['MaxIndex'] = \
            np.zeros(self.outputs['Out'].shape).astype('int32')
57 58 59
        self.check_grad(["X"], "Out")


D
dzhwinter 已提交
60
class TestSeqSumPool(TestSeqAvgPool):
61
    def compute(self, x, offset, out):
D
dzhwinter 已提交
62
        self.attrs = {'pooltype': "SUM"}
63 64
        for i in range(len(offset[0]) - 1):
            sub_x = x[offset[0][i]:offset[0][i + 1], :]
D
dzhwinter 已提交
65 66 67 68 69 70 71
            out[i] = sub_x.sum(axis=0)


class TestSeqMaxPool(TestSeqAvgPool):
    def set_data(self):
        self.op_type = 'sequence_pool'
        x = np.random.uniform(0.1, 1, [13, 23]).astype('float32')
72 73 74 75 76
        lod = [[4, 1, 3, 5]]
        offset = self.convert_to_offset(lod)
        for i in range(len(offset[0]) - 1):
            l = offset[0][i + 1] - offset[0][i]
            x[offset[0][i] + np.random.randint(l), :] += 2.0
D
dzhwinter 已提交
77 78 79 80 81

        self.inputs = {'X': (x, lod)}

        out = np.zeros((4, 23)).astype('float32')
        self.outputs = {'Out': out}
82
        return x, offset, out
D
dzhwinter 已提交
83

84
    def compute(self, x, offset, out):
D
dzhwinter 已提交
85
        self.attrs = {'pooltype': "MAX"}
86 87
        for i in range(len(offset[0]) - 1):
            sub_x = x[offset[0][i]:offset[0][i + 1], :]
D
dzhwinter 已提交
88 89 90 91
            out[i] = np.amax(sub_x, axis=0)


class TestSeqSqrtPool(TestSeqAvgPool):
92
    def compute(self, x, offset, out):
D
dzhwinter 已提交
93
        self.attrs = {'pooltype': "SQRT"}
94 95 96 97
        for i in range(len(offset[0]) - 1):
            sub_x = x[offset[0][i]:offset[0][i + 1], :]
            seq_len = offset[0][i + 1] - offset[0][i]
            out[i] = sub_x.sum(axis=0) / np.sqrt(seq_len)
D
dzhwinter 已提交
98 99 100


class TestSeqLastPool(TestSeqAvgPool):
101
    def compute(self, x, offset, out):
D
dzhwinter 已提交
102
        self.attrs = {'pooltype': "LAST"}
103 104
        for i in range(len(offset[0]) - 1):
            sub_x = x[offset[0][i]:offset[0][i + 1], :]
D
dzhwinter 已提交
105 106 107 108
            out[i] = sub_x[-1, :]


class TestSeqFirstPool(TestSeqAvgPool):
109
    def compute(self, x, offset, out):
D
dzhwinter 已提交
110
        self.attrs = {'pooltype': "FIRST"}
111 112
        for i in range(len(offset[0]) - 1):
            sub_x = x[offset[0][i]:offset[0][i + 1], :]
D
dzhwinter 已提交
113 114 115
            out[i] = sub_x[0, :]


116 117 118
class TestSeqAvgPool2D(TestSeqAvgPool):
    def set_data(self):
        self.op_type = 'sequence_pool'
119 120
        # one level, batch size is 4
        x = np.random.uniform(0.1, 1, [13, 3, 17]).astype('float32')
121
        lod = [[4, 1, 3, 5]]
122
        self.inputs = {'X': (x, lod)}
123
        offset = self.convert_to_offset(lod)
124 125

        out = np.zeros((4, 3, 17)).astype('float32')
126
        self.outputs = {'Out': out}
127
        return x, offset, out
128

129
    def compute(self, x, offset, out):
D
dzhwinter 已提交
130
        self.attrs = {'pooltype': "AVERAGE"}
131 132 133
        for i in range(len(offset[0]) - 1):
            sub_x = np.reshape(x[offset[0][i]:offset[0][i + 1], :],
                               (-1, 3 * 17))
134 135 136
            out[i] = np.reshape(sub_x.mean(axis=0), (3, 17))


137
class TestSeqSumPool2D(TestSeqAvgPool2D):
138
    def compute(self, x, offset, out):
D
dzhwinter 已提交
139
        self.attrs = {'pooltype': "SUM"}
140 141 142
        for i in range(len(offset[0]) - 1):
            sub_x = np.reshape(x[offset[0][i]:offset[0][i + 1], :],
                               (-1, 3 * 17))
143
            out[i] = np.reshape(sub_x.sum(axis=0), (3, 17))
144 145


L
Luo Tao 已提交
146
class TestSeqSqrtPool2D(TestSeqAvgPool2D):
147
    def compute(self, x, offset, out):
D
dzhwinter 已提交
148
        self.attrs = {'pooltype': "SQRT"}
149 150 151 152 153
        for i in range(len(offset[0]) - 1):
            sub_x = np.reshape(x[offset[0][i]:offset[0][i + 1], :],
                               (-1, 3 * 17))
            seq_len = offset[0][i + 1] - offset[0][i]
            out[i] = np.reshape(sub_x.sum(axis=0) / np.sqrt(seq_len), (3, 17))
L
Luo Tao 已提交
154 155

    def test_check_grad(self):
156 157 158
        # Remove MaxIndex after check_grad is refined.
        self.outputs['MaxIndex'] = \
            np.zeros(self.outputs['Out'].shape).astype('int32')
L
Luo Tao 已提交
159 160 161
        self.check_grad(["X"], "Out", max_relative_error=0.06)


L
Luo Tao 已提交
162
class TestSeqMaxPool2D(TestSeqAvgPool2D):
163 164 165
    def set_data(self):
        self.op_type = 'sequence_pool'
        x = np.random.uniform(0.1, 1, [13, 3, 11]).astype('float32')
166
        lod = [[4, 1, 3, 5]]
167
        self.inputs = {'X': (x, lod)}
168 169 170 171
        offset = self.convert_to_offset(lod)
        for i in range(len(offset[0]) - 1):
            l = offset[0][i + 1] - offset[0][i]
            x[offset[0][i] + np.random.randint(l), :] += 1.0
172 173 174

        out = np.zeros((4, 3, 11)).astype('float32')
        self.outputs = {'Out': out}
175
        return x, offset, out
176

177
    def compute(self, x, offset, out):
D
dzhwinter 已提交
178
        self.attrs = {'pooltype': "MAX"}
179 180 181
        for i in range(len(offset[0]) - 1):
            sub_x = np.reshape(x[offset[0][i]:offset[0][i + 1], :],
                               (-1, 3 * 11))
182
            out[i] = np.reshape(np.amax(sub_x, axis=0), (3, 11))
L
Luo Tao 已提交
183 184


L
Luo Tao 已提交
185
class TestSeqLastPool2D(TestSeqAvgPool2D):
186
    def compute(self, x, offset, out):
D
dzhwinter 已提交
187
        self.attrs = {'pooltype': "LAST"}
188 189 190
        for i in range(len(offset[0]) - 1):
            sub_x = np.reshape(x[offset[0][i]:offset[0][i + 1], :],
                               (-1, 3 * 17))
L
Luo Tao 已提交
191 192 193 194
            out[i] = np.reshape(sub_x[-1, :], (3, 17))


class TestSeqFirstPool2D(TestSeqAvgPool2D):
195
    def compute(self, x, offset, out):
D
dzhwinter 已提交
196
        self.attrs = {'pooltype': "FIRST"}
197 198 199
        for i in range(len(offset[0]) - 1):
            sub_x = np.reshape(x[offset[0][i]:offset[0][i + 1], :],
                               (-1, 3 * 17))
L
Luo Tao 已提交
200 201 202
            out[i] = np.reshape(sub_x[0, :], (3, 17))


203 204
if __name__ == '__main__':
    unittest.main()