Write your own machine learning ZK smart contract
A decision tree classifier is just one of many powerful machine learning (ML) algorithms. Other algorithms may be more suitable for your application. If you wish to create your own ZK smart contract for inference on a different type of ML model, there are a few things you need to keep in mind about the ZK Rust language and PBC.
Integer arithmetic
The ZK Rust language performs computations on integers. If your model comprises parts that involve non-integers, you must apply a fixed-point scaling factor. Otherwise, a value such as 0.2 will be interpreted as 0. The same is true for feature values in the input sample, which should apply the same scaling factor. Indeed, if you interact with the contract through the browser to upload a model or an input sample, it will only accept integer values. This also means that model inference should be expressed using only arithmetic operations on integers. For example, if your ML algorithm relies on non-linear functions, such as the sigmoid function used in logistic regression, you must find an approximation that can be expressed through multiplications and additions.
You can read more about the feature set of the ZK Rust language in our language guide.
Model and sample representation
How you represent your model and the input sample in the ZK smart contract defines how you upload them when interacting with the contract through the browser. For instance, our example contract described in the previous section represents the binary decision tree classifier as two arrays, one containing the internal vertices and one containing the leaf vertices, which are both specified as structured types.
/// Representation of internal vertices.
#[derive(SecretBinary, Debug, Clone, CreateTypeSpec)]
pub struct InternalVertex {
/// The secret-shared feature index
feature: Sbu8,
/// The secret-shared threshold value
threshold: Sbi16,
}
/// Representation of leaf vertices.
#[derive(SecretBinary, Debug, Clone, CreateTypeSpec)]
pub struct LeafVertex {
/// The secret-shared class
classification: Sbu1,
}
/// Input model (decision tree classifier) used for evaluation.
#[derive(SecretBinary, Debug, Clone, CreateTypeSpec)]
pub struct Model {
internals: [InternalVertex; 7],
leaves: [LeafVertex; 8],
}
This means that when uploading the model through the browser, the (splitting feature, threshold value) pair of each internal vertex must be typed in manually, and the class prediction of each leaf vertex must be selected individually.
You can read more about how to deploy your ZK smart contract on our testnet and how you can interact with it through the browser in the next section.