Hi there,
I have a Deep Learning network of the following structure:
model = models.Sequential() model.add(layers.Conv2D(32, (3, 3), activation='relu', input_shape=(dim_x,dim_y,3))) model.add(layers.MaxPooling2D((2,2))) model.add(layers.Conv2D(16, (3,3), activation='relu')) model.add(layers.AveragePooling2D((2,2))) model.add(layers.Conv2D(8, (3,3), activation='relu')) model.add(layers.AveragePooling2D((2,2))) model.add(layers.Flatten()) model.add(layers.Dense(64, activation='relu')) model.add(layers.Dense(2)) model.add(layers.Softmax())
The output of this network when in the Python Tensorflow environment is an array of 2 numbers, each element of the array is the probability that the input to the classifier network is either "false" or "true".
i.e. its a very simple classifier network that looks for the presence of a white square on a black background
I have converted this network for use on an AM57xx processor using the TIDL tool and now I wish to know how to correctly interpret the output of the network. I do not have any TI example code as I am using a BeagleBone AI
Below are the code snippets for the important parts of the code I am currently running:
configuration.numFrames = 0;
configuration.inData = "/var/lib/cloud9/img_0.png";
configuration.netBinFile = "/var/lib/cloud9/Ziath/models/BBAI_model_test/probability_colour_cnn_classifier_net.bin";
configuration.paramsBinFile = "/var/lib/cloud9/Ziath/models/BBAI_model_test/probability_colour_cnn_classifier_param.bin";
configuration.preProcType = 2;
configuration.inWidth = 100;
configuration.inHeight = 100;
configuration.inNumChannels = 3;
configuration.enableApiTrace = true;
configuration.runFullNet = true;
imgutil::PreprocessImage(src, eop->GetInputBufferPtr(), configuration);
int = tf_postprocess((uchar*) eop->GetOutputBufferPtr(), selected_items_size, selected_items, configuration, label_count);
int tf_postprocess(uchar *in, int selected_items_size, int * selected_items, Configuration & configuration, int label_count)
{
int top_candidates = 3;
const int k = top_candidates;
int rpt_id = -1;
typedef std::pair<uchar, int> val_index;
auto cmp = [](val_index &left, val_index &right) { return left.first > right.first; };
std::priority_queue<val_index, std::vector<val_index>, decltype(cmp)> queue(cmp);
#ifdef DEBUG
std::bitset<8> x(in[0]);
std::cout << "Start PostProcess" << std::endl;
std::cout << "input: " << x << std::endl;
#endif
// initialize priority queue with smallest value on top
for (int i = 0; i < k; i++) {
if(configuration.enableApiTrace) {
std::bitset<8> y(in[i]);
std::cout << "push(" << i << "):" << y << std::endl;
}
queue.push(val_index(in[i], i));
}
// for rest input, if larger than current minimum, pop mininum, push new val
for (int i = k; i < label_count; i++)
{
if (in[i] > queue.top().first)
{
queue.pop();
queue.push(val_index(in[i], i));
}
}
// output top k values in reverse order: largest val first
std::vector<val_index> sorted;
while (! queue.empty())
{
sorted.push_back(queue.top());
queue.pop();
}
for (int i = 0; i < k; i++)
{
int id = sorted[i].second;
#ifdef DEBUG
std::cout << "id is: " << id << std::endl;
#endif
if (tf_expected_id(id, selected_items_size, selected_items))
{
rpt_id = id;
}
}
printf("#####rpt_id = %i\n\r", rpt_id);
return rpt_id;
}
The top 3 returned candidates for my input images are as follows:
img_0 (square present) push(0):11001000 push(1):01110101 push(2):00011001 img_1 (no square) push(0):11001000 push(1):00000101 push(2):10001011 img_2 (square present) push(0):11001000 push(1):00000101 push(2):01101111 img_3 (square present) push(0):11001000 push(1):10100101 push(2):11010010 img_4 (square present) push(0):11001000 push(1):00100101 push(2):11101111 img_5 (no square) push(0):11001000 push(1):11000101 push(2):01110001 img_6 (square present) push(0):11001000 push(1):10000101 push(2):00111010 img_7 (no square) push(0):11001000 push(1):00000101 push(2):01100110
If anyone could point me in the correct direction for interpreting the output of the network on the AM57xx device, that would be brilliant
Thanks!