SameDiffLambdaVertex with const parameter serialization

Hello,

i try my first step in implementing some custom layer and vertices in your framework. I had with the glad of some copy and paste able to create my first SameDiffLambdaVertex. I have to parameters for the class: the vector size and the sequence lenght. So the training now runs fine and i can save the model. As soon as i try to load i have the problem where to store the two variables. I have seen the examples from samediff in the repository and the layers have methods to initialize the parameter but i found nothing in comparsion on the SameDiffLambdaVertex class.

In other examples i saw the annotation @JsonProperty but i am not sure if this is a solution and how to use.

Would appreciate any hints!

Best regards

Thomas

@thomas Could you elaborate on your use case a bit? What specifically are you trying to do? Usually a SamediffLambda Layer would take in a seet of parameters you pass in and those could be placeholders. In the framework we have a few examples like the CapsuleLayers: deeplearning4j/CapsuleLayer.java at 759885ffb9e53f7728e6147d03bd6346eaf0f0ca · deeplearning4j/deeplearning4j · GitHub

I want to save some parameters which not inside the learning process only for net architecture. My current try is:

public PositionalEncodingVertex(@JsonProperty("sequenceLen") Long seqLen, @JsonProperty("vectorSize") Long vectorSize) {

The constructor is currently inside the following class definition:

public class PositionalEncodingVertex extends SameDiffLambdaVertex {

Test is currently running, i hope this clarifies more what i try to do.

Best regards

The test is one step further, the deserialization tries to use the given constructor but throws an exception:

Caused by: org.nd4j.shade.jackson.databind.exc.ValueInstantiationException: Cannot construct instance of simple.generator.models.PositionalEncodingVertex, problem: java.lang.NullPointerException
at [Source: (String)"{

do i have to register the json variables any further?

@thomas you have to register everything you want serialized as json in the class. Could you post your whole class? If you have certain fields that shouldn’t be added you can use @JsonIgnore. Usually all fields should be defined in the constructor though. If you want further help feel free to post an example for me either here or privately and I can try to run it.

Thanks, i got success with implementing simple get / set Methods and annotated them with the @JsonProperty. Seems to work for now:

/**
 * positional encoding for the transfomer input layer 
 * 
 * @author
 */
public class PositionalEncodingVertex extends SameDiffLambdaVertex {

	/**
	 * generated serialization id
	 */
	private static final long serialVersionUID = 187573473875L;
	
	/**
	 * max sequence length 
	 */
	private long seqLen;
	
	/**
	 * output vector size 
	 */
	private long vectorSize;

	/**
	 * default constructor 
	 */
	public PositionalEncodingVertex() {
		seqLen = 0L;
		vectorSize = 0L;
	}
	
	/**
	 * default constructor 
	 * 
	 * @param sl max seq len
	 * @param vs vectorSize
	 */
	public PositionalEncodingVertex(long sl, long vs) {
		seqLen     = sl;
		vectorSize = vs;
	}

	@Override 
	public GraphVertex clone() {
		return new PositionalEncodingVertex(seqLen, vectorSize);
	}
	  
	@Override
	public SDVariable defineVertex(SameDiff sameDiff, VertexInputs inputs) {
		INDArray posenc = Nd4j.zeros(vectorSize, seqLen);
	    
		for (long i=0;i<(vectorSize + 1) / 2;i++) {
			double multiplier = Math.pow(10000, -2 * ((double) i) / vectorSize);

			for (long t = 0; t < seqLen; t++) {
				
				double inner = t * multiplier;
				
				posenc.putScalar(2 * i, t, Math.sin(inner));
				
				if (2 * i + 1 < vectorSize) {
					posenc.putScalar(2 * i + 1, t, Math.cos(inner));
				}
			}
	    }
	    return inputs.getInput(0).add(sameDiff.constant(posenc));
	}

	  
	@Override
	public InputType getOutputType(int layerIndex, InputType... vertexInputs) throws InvalidInputTypeException {
		return vertexInputs[0];
	}
	    
	    
	@Override
	public Pair<INDArray, MaskState> feedForwardMaskArrays(INDArray[] maskArrays, MaskState currentMaskState,int minibatchSize) {
		return new Pair<>(maskArrays[0], currentMaskState);
	}
	  
	@JsonProperty
	public long getSeqLen() {
		return seqLen;
	}

	@JsonProperty
	public void setSeqLen(Long sl) {
		this.seqLen = sl;
	}
	
	@JsonProperty
	public long getVectorSize() {
		return vectorSize;
	}

	@JsonProperty
	public void setVectorSize(Long vs) {
		this.vectorSize = vs;
	}	  
	  
}