2017-11-19 3 views
1

나는 link을 따라 마스크라는 사용자 정의 op를 작성했습니다. tensorflow 연산의 본체는 실제로 꽤 많이 인용 된 링크를 따라ValueError : op 이름에 대해 생성 된 그라디언트 1의 수 : "마스크/마스크"

def tf_mask(x, labels, epoch_, name=None): # add "labels" to the input 
    with ops.name_scope(name, "Mask", [x, labels, epoch_]) as name: 
     z = py_func(np_mask, 
       [x, labels, epoch_], # add "labels, epoch_" to the input list 
       [tf.float32], 
       name=name, 
       grad=our_grad) 
     z = z[0] 
     z.set_shape(x.get_shape()) 
     return z 

입니다. 그러나, 나는이 오류로 실행 : I 그라데이션을 계산하는 our_grad 함수를 정의하는 방법을

ValueError: Num gradients 1 generated for op name: "mask/Mask" 
op: "PyFunc" 
input: "conv2/Relu" 
input: "Placeholder_2" 
input: "Placeholder_3" 
attr { 
    key: "Tin" 
    value { 
    list { 
     type: DT_FLOAT 
     type: DT_FLOAT 
     type: DT_FLOAT 
    } 
    } 
} 
attr { 
    key: "Tout" 
    value { 
    list { 
     type: DT_FLOAT 
    } 
    } 
} 
attr { 
    key: "_gradient_op_type" 
    value { 
    s: "PyFuncGrad302636" 
    } 
} 
attr { 
    key: "token" 
    value { 
    s: "pyfunc_0" 
    } 
} 
do not match num inputs 3 

이 필요한 경우,이입니다.

def our_grad(cus_op, grad): 
    """Compute gradients of our custom operation. 
    Args: 
    param cus_op: our custom op tf_mask 
    param grad: the previous gradients before the operation 
    Returns: 
    gradient that can be sent down to next layer in back propagation 
    it's an n-tuple, where n is the number of arguments of the operation 
    """ 
    x = cus_op.inputs[0] 
    labels = cus_op.inputs[1] 
    epoch_ = cus_op.inputs[2] 
    n_gr1 = tf_d_mask(x) 
    n_gr2 = tf_gradient2(x, labels, epoch_) 

    return tf.multiply(grad, n_gr1) + n_gr2 

그리고 py_func 기능 (인용 링크와 같은)은

def py_func(func, inp, tout, stateful=True, name=None, grad=None): 
    """ 
    I omitted the introduction to parameters that are not of interest 
    :param func: a numpy function 
    :param inp: input tensors 
    :param grad: a tensorflow function to get the gradients (used in bprop, should be able to receive previous 
       gradients and send gradients down.) 

    :return: a tensorflow op with a registered bprop method 
    """ 
    # Need to generate a unique name to avoid duplicates: 
    rnd_name = 'PyFuncGrad' + str(np.random.randint(0, 1000000)) 
    tf.RegisterGradient(rnd_name)(grad) 
    g = tf.get_default_graph() 
    with g.gradient_override_map({"PyFunc": rnd_name}): 
     return tf.py_func(func, inp, tout, stateful=stateful, name=name) 

은 정말 지역 사회의 도움이 필요합니다!

감사합니다.

답변

1

약간의 노력 끝에 알맞게이 문제를 직접 해결했습니다.

오류 메시지가 tensorflow 함수 gradients_impl.py에서 생성되었습니다.

def _VerifyGeneratedGradients(grads, op): 
    """Verify that gradients are valid in number and type. 

    Args: 
    grads: List of generated gradients. 
    op: Operation for which the gradients where generated. 

    Raises: 
    ValueError: if sizes of gradients and inputs don't match. 
    TypeError: if type of any gradient is not valid for its input. 
    """ 
    if len(grads) != len(op.inputs): 
    raise ValueError("Num gradients %d generated for op %s do not match num " 
        "inputs %d" % (len(grads), op.node_def, len(op.inputs))) 

이제 우리는 우리가 그것을 3 개 개의 입력을 준,이 오류가 우리의 연산 Mask 수단을 볼 수 있습니다. TensorFlow는 그라디언트 our_grad을 생성하는 함수에 대해 세 개의 출력을 제공 할 것으로 예상하며, 각 출력에는 전달 전달 함수가 입력됩니다. 실제로 우리가 첫 번째 입력에 대한 기울기를 원하는

주, 다른 두 그라디언트가 wecan 두 개 fake_gradients 올바른 모양으로 돌아가 다시 전파에 더 이상 사용되지 않습니다.

관련 문제