Open GeorgeBohw opened 3 years ago
def attention_infer()如下:
def attention_infer(images, num_classes, use_cudnn=True):
max_length = 20
gru_backward, encoded_vector, encoded_proj = encoder_net(
images, is_test=True, use_cudnn=use_cudnn)
backward_first = fluid.layers.sequence_pool(
input=gru_backward, pool_type='first')
decoder_boot = fluid.layers.fc(input=backward_first,
size=decoder_size,
bias_attr=False,
act="relu")
init_state = decoder_boot
array_len = fluid.layers.fill_constant(
shape=[1], dtype='int64', value=max_length)
counter = fluid.layers.zeros(shape=[1], dtype='int64', force_cpu=True)
# fill the first element with init_state
state_array = fluid.layers.create_array('float32')
fluid.layers.array_write(init_state, array=state_array, i=counter)
# ids, scores as memory
ids_array = fluid.layers.create_array('int64')#此OP创建一个LoDTensorArray,它可以用作 array_write , array_read OP的输入,以及和 While OP 一起创建RNN网络
scores_array = fluid.layers.create_array('float32')
init_ids = fluid.data( #全局block中创建变量(Variable),该全局变量可被计算图中的算子(operator)访问。该变量可作为占位符用于数据输入
name="init_ids", shape=[None, 1], dtype="int64", lod_level=2)
init_scores = fluid.data(
name="init_scores", shape=[None, 1], dtype="float32", lod_level=2)
fluid.layers.array_write(init_ids, array=ids_array, i=counter)
fluid.layers.array_write(init_scores, array=scores_array, i=counter)
cond = fluid.layers.less_than(x=counter, y=array_len)
while_op = fluid.layers.While(cond=cond)
with while_op.block():
pre_ids = fluid.layers.array_read(array=ids_array, i=counter)
pre_state = fluid.layers.array_read(array=state_array, i=counter)
pre_score = fluid.layers.array_read(array=scores_array, i=counter)
pre_ids_emb = fluid.layers.embedding(
input=pre_ids,
size=[num_classes + 2, word_vector_dim],
dtype='float32')
context = simple_attention(encoded_vector, encoded_proj, pre_state,
decoder_size)
# expand the recursive_sequence_lengths of pre_state to be the same with pre_score
pre_state_expanded = fluid.layers.sequence_expand(pre_state, pre_score)
context_expanded = fluid.layers.sequence_expand(context, pre_score)
fc_1 = fluid.layers.fc(input=context_expanded,
size=decoder_size * 3,
bias_attr=False)
fc_2 = fluid.layers.fc(input=pre_ids_emb,
size=decoder_size * 3,
bias_attr=False)
decoder_inputs = fc_1 + fc_2
current_state, _, _ = fluid.layers.gru_unit(
input=decoder_inputs,
hidden=pre_state_expanded,
size=decoder_size * 3)
current_state_with_lod = fluid.layers.lod_reset(
x=current_state, y=pre_score)
# use score to do beam search
current_score = fluid.layers.fc(input=current_state_with_lod,
size=num_classes + 2,
bias_attr=True,
act='softmax')
topk_scores, topk_indices = fluid.layers.topk(
current_score, k=beam_size)
# calculate accumulated scores after topk to reduce computation cost
accu_scores = fluid.layers.elementwise_add(
x=fluid.layers.log(topk_scores),
y=fluid.layers.reshape(
pre_score, shape=[-1]),
axis=0)
selected_ids, selected_scores = fluid.layers.beam_search(
pre_ids,
pre_score,
topk_indices,
accu_scores,
beam_size,
eos, # end_id
#level=0
)
fluid.layers.increment(x=counter, value=1, in_place=True)
# update the memories
fluid.layers.array_write(current_state, array=state_array, i=counter)
fluid.layers.array_write(selected_ids, array=ids_array, i=counter)
fluid.layers.array_write(selected_scores, array=scores_array, i=counter)
# update the break condition: up to the max length or all candidates of
# source sentences have ended.
length_cond = fluid.layers.less_than(x=counter, y=array_len)
finish_cond = fluid.layers.logical_not(
fluid.layers.is_empty(x=selected_ids))
fluid.layers.logical_and(x=length_cond, y=finish_cond, out=cond)
ids, scores = fluid.layers.beam_search_decode(ids_array, scores_array,
beam_size, eos)
return ids
os: ubuntu with gpu paddle1.8
转换paddle到c++运行,下面两种情况,pyhon运行均正常,c++运行报错。 attention.py中的def attention_infer()函数:
情况1: pre_ids_emb = fluid.layers.embedding() 转化的模型在c++环境下运行出现错误:
0 std::string paddle::platform::GetTraceBackString<std::string const&>(std::string const&, char const, int) 1 paddle::platform::EnforceNotMet::EnforceNotMet(std::string const&, char const, int) 2 paddle::operators::LookupTableOp::InferShape(paddle::framework::InferShapeContext) const 3 paddle::framework::OperatorWithKernel::RunImpl(paddle::framework::Scope const&, paddle::platform::Place const&, paddle::framework::RuntimeContext) const 4 paddle::framework::OperatorWithKernel::RunImpl(paddle::framework::Scope const&, paddle::platform::Place const&) const 5 paddle::framework::OperatorBase::Run(paddle::framework::Scope const&, paddle::platform::Place const&) 6 paddle::framework::Executor::RunPartialPreparedContext(paddle::framework::ExecutorPrepareContext, paddle::framework::Scope, long, long, bool, bool, bool) 7 paddle::framework::Executor::RunPreparedContext(paddle::framework::ExecutorPrepareContext, paddle::framework::Scope, bool, bool, bool) 8 paddle::operators::WhileOp::RunImpl(paddle::framework::Scope const&, paddle::platform::Place const&) const 9 paddle::framework::OperatorBase::Run(paddle::framework::Scope const&, paddle::platform::Place const&) 10 paddle::framework::NaiveExecutor::Run() 11 paddle::AnalysisPredictor::ZeroCopyRun()
Error: ShapeError: The last dimensions of the 'Ids' tensor must be 1. But received Ids's last dimensions = 128, Ids's shape = [1, 128]. [Hint: Expected ids_dims[ids_rank - 1] == 1, but received ids_dims[ids_rank - 1]:128 != 1:1.] at (/home/george/paddle/paddle/fluid/operators/lookup_table_op.cc:51) [operator < lookup_table > error
情况2: pre_ids_emb = fluid.layers.embedding()改为pre_ids_emb = fluid.embedding() 转化的模型在c++环境下运行出现错误:
0 std::string paddle::platform::GetTraceBackString<std::string const&>(std::string const&, char const, int) 1 paddle::platform::EnforceNotMet::EnforceNotMet(std::string const&, char const, int) 2 long const paddle::framework::Tensor::data() const
3 paddle::operators::LookupTableV2CUDAKernel::Compute(paddle::framework::ExecutionContext const&) const
4 std::_Function_handler<void (paddle::framework::ExecutionContext const&), paddle::framework::OpKernelRegistrarFunctor<paddle::platform::CUDAPlace, false, 0ul, paddle::operators::LookupTableV2CUDAKernel, paddle::operators::LookupTableV2CUDAKernel, paddle::operators::LookupTableV2CUDAKernel >::operator()(char const , char const, int) const::{lambda(paddle::framework::ExecutionContext const&)#1}>::_M_invoke(std::_Any_data const&, paddle::framework::ExecutionContext const&)
5 paddle::framework::OperatorWithKernel::RunImpl(paddle::framework::Scope const&, paddle::platform::Place const&, paddle::framework::RuntimeContext) const
6 paddle::framework::OperatorWithKernel::RunImpl(paddle::framework::Scope const&, paddle::platform::Place const&) const
7 paddle::framework::OperatorBase::Run(paddle::framework::Scope const&, paddle::platform::Place const&)
8 paddle::framework::Executor::RunPartialPreparedContext(paddle::framework::ExecutorPrepareContext, paddle::framework::Scope, long, long, bool, bool, bool)
9 paddle::framework::Executor::RunPreparedContext(paddle::framework::ExecutorPrepareContext, paddle::framework::Scope, bool, bool, bool)
10 paddle::operators::WhileOp::RunImpl(paddle::framework::Scope const&, paddle::platform::Place const&) const
11 paddle::framework::OperatorBase::Run(paddle::framework::Scope const&, paddle::platform::Place const&)
12 paddle::framework::NaiveExecutor::Run()
13 paddle::AnalysisPredictor::ZeroCopyRun()
InvalidArgumentError: Tensor holds the wrong type, it holds float, but desires to be int64_t. [Hint: Expected valid == true, but received valid:0 != true:1.] at (/home/george/paddle/paddle/fluid/framework/tensor_impl.h:33) [operator < lookup_table_v2 > error]