Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

如何在paddle.v2中输出网络中多个中间层 #4153

Closed
daiwk opened this issue Sep 18, 2017 · 8 comments
Closed

如何在paddle.v2中输出网络中多个中间层 #4153

daiwk opened this issue Sep 18, 2017 · 8 comments
Labels
User 用于标记用户问题

Comments

@daiwk
Copy link
Contributor

daiwk commented Sep 18, 2017

例如,我想输出最后的prob以及中间的一个embedding,模型结构中:

def topology(dict_dim, class_num, is_infer=True):
    data = paddle.layer.data("word",
                             paddle.data_type.integer_value_sequence(input_dim))
    emb = paddle.layer.embedding(input=data, size=emb_dim)
    # ...
    output = paddle.layer.fc(
        input=[fc_last, lstm_last],
        size=class_dim,
        act=paddle.activation.Softmax(),
        bias_attr=bias_attr,
        param_attr=para_attr)
    if is_infer:
        return output, emb 

infer部分:

prob_layer, emb  = topology(dict_dim, class_num, is_infer=True)
inferer = paddle.inference.Inference(output_layer=[prob_layer, emb], parameters=parameters)  
probs = inferer.infer(input=test_batch, field=["value", "value"])

但会报错

  File "local_scripts/infer.py", line 19, in _infer_a_batch
    probs = inferer.infer(input=test_batch, field=["value", "value"])
  File "/home/work/daiwenkai/paddle_v2/python27/lib/python2.7/site-packages/paddle/v2/inference.py", line 79, in infer
    retv = [numpy.concatenate(out) for out in retv]
ValueError: all the input array dimensions except for the concatenation axis must match exactly
@lcy-seso
Copy link
Contributor

lcy-seso commented Sep 18, 2017

解决方法是这样:

  1. infer的用法有一个错误:

    probs = inferer.infer(input=test_batch, field=["value", "value"])

    这一行应该改为:

    probs = inferer.infer(input=test_batch, field=["value"])

    按照目前代码实现的逻辑,v2 接口的这个 field 域不是对每一个output layer 分别指定要输出的字段,而是:指定一个输出字段的list,会为每一个输出layer取list里面的每一个字段。

  2. 调用infer接口时,设置 flatten_result=False
    https://github.com/PaddlePaddle/Paddle/blob/develop/python/paddle/v2/inference.py#L99

@lcy-seso
Copy link
Contributor

lcy-seso commented Sep 18, 2017

上面报错的原因是:

  • 如果指定了2个layer作为输出层,实际上需要的输出结果是两个矩阵;
  • 假设第一个layer的输出A是一个 N1 * M1 的矩阵,第二个 Layer 的输出B是一个 N2 * M2 的矩阵;
  • v2 默认会将A和B 横向拼接,当N1 和 N2 大小不一样时,会报上面的错误。

@lcy-seso
Copy link
Contributor

lcy-seso commented Sep 18, 2017

设置 flatten_result=False 之后会去掉“拼接”这个步骤,返回的结果是一个list:

  • list元素的个数等于网络中输出层的个数;
  • list 中每个元素是一个layer的输出结果矩阵,类型是numpy的ndarray;
  • 每一个layer输出矩阵的高度,在非序列输入时:等于样本数;序列输入时等于:输入序列中元素的总数;宽度等于配置中layer的size;

@lcy-seso lcy-seso added the User 用于标记用户问题 label Sep 18, 2017
@lcy-seso lcy-seso changed the title 如何在paddle.v2中输出中间层 如何在paddle.v2中输出网络中多个中间层 Sep 18, 2017
@daiwk
Copy link
Contributor Author

daiwk commented Sep 18, 2017

谢谢,我试试~

@daiwk
Copy link
Contributor Author

daiwk commented Sep 18, 2017

对于中间层的shape,有点疑问,例如,

emb_dim=128
hid_dim=512
input_dim=397

data = paddle.layer.data("word",paddle.data_type.integer_value_sequence(input_dim))
emb = paddle.layer.embedding(input=data, size=emb_dim) 
fc1 = paddle.layer.fc(input=emb, size=hid_dim, act=linear, bias_attr=bias_attr)

batch_size=10时,

emb.shape=(250, 128)
fc1.shape=(250,512)

为啥第一个是250呢?

@qingqing01
Copy link
Contributor

@daiwk

  • data层是integer_value_sequence,表示sequence类型。
  • 250是batch_size(也就是10)个样本中所有word的总数。
  • 统计data层,当前mini-batch的word总数,就是emb, fc1的高250。

@daiwk
Copy link
Contributor Author

daiwk commented Sep 18, 2017

明白了,正好我这10条样本的总词数是250个……谢谢
比如,第一个样本有20个词,那这个250*128的矩阵的前20行构成的小矩阵就是它对应的embedding吧
第二个样本有3个词,同样对应第21到23行的小矩阵

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
User 用于标记用户问题
Projects
None yet
Development

No branches or pull requests

3 participants