<jupyter_start><jupyter_text>Safety Gear Detection Sample Application  OpenVINO version check:You are currently using the latest development version of Intel® Distribution of OpenVINO™ Toolkit. Alternatively, you can open a version of this notebook for the Intel® Distribution of OpenVINO™ Toolkit LTS version by [clicking this link](../../../../openvino-lts/developer-samples/python/safety-gear-detection-python/safety_gear_detection.ipynb).  PrerequisitesThis sample requires the following:- All files are present and in the following directory structure:    - **safety_gear_detection.ipynb** - This Jupyter* Notebook    - **safety_gear_detection.py** - Python* code for safety gear detection application    - **safety_gear_detection_annotate.py** - Python* code to perform post-processing to annotate output video    - **/data/reference-sample-data/safety-gear-detection/labels.txt** - Model-specific mapping of numerical labels to text strings    - **/data/reference-sample-data/safety-gear-detection/worker_safety_mobilenet.caffemodel** - Binary containing trained weights for inference model used    - **/data/reference-sample-data/safety-gear-detection/worker_safety_mobilenet.prototxt** - The deployed [Protocol Buffer](https://developers.google.com/protocol-buffers) file that describes the network architecture for inference model used    - **/data/reference-sample-data/safety-gear-detection/Safety_Full_Hat_and_Vest.mp4** - Test videoIt is recommended that you have already read the following from [Get Started on the Intel® DevCloud for the Edge](https://devcloud.intel.com/edge/home/):- [Overview of the Intel® DevCloud for the Edge](https://devcloud.intel.com/edge/get_started/devcloud/)- [Overview of the Intel® Distribution of OpenVINO™ toolkit](https://devcloud.intel.com/edge/get_started/openvino/)Note: It is assumed that the server this sample is being run on is on the Intel® DevCloud for the Edge which has Jupyter* Notebook customizations and all the required libraries already installed.  If you download or copy to a new server, this sample may not run.  IntroductionThis sample application demonstrates how a smart video IoT solution may be created using Intel® hardware and software tools to perform safety gear detection.  This solution detects any number of objects within a video frame looking specifically for people, safety vests, and hardhats. The results for each frame are stored in a text file that is later read by a second pass to annotate the input video with boxes around detected objects with a label and probability value. Key conceptsThis sample application includes an example for the following:- Application:  - Video and image input is supported using OpenCV  - OpenCV is used to draw bounding boxes around detected objects, labels, and other information  - Visualization of the resulting bounding boxes in the output  - Uses the [Async API](https://docs.openvinotoolkit.org/latest/_docs_IE_DG_Intro_to_Performance.html) feature of the Inference Engine (see [Object Detection Sample](../object-detection-python/object_detection.ipynb) for more details)- Intel® DevCloud for the Edge:  - Submitting inference as jobs that are performed on different edge compute nodes (rather than on the development node hosting this Jupyter* notebook)  - Monitoring job status  - Viewing results and assessing performance for hardware on different compute nodes- [Intel® Distribution of OpenVINO™ toolkit](https://software.intel.com/openvino-toolkit):  - Create the necessary Intermediate Representation (IR) files for the inference model using the [Model Downloader](http://docs.openvinotoolkit.org/latest/_tools_downloader_README.html) and [Model Optimizer](http://docs.openvinotoolkit.org/latest/_docs_MO_DG_Deep_Learning_Model_Optimizer_DevGuide.html)  - Run an inference application on multiple hardware devices using the [Inference Engine](http://docs.openvinotoolkit.org/latest/_docs_IE_DG_Deep_Learning_Inference_Engine_DevGuide.html)  Safety gear detection applicationThe safety gear detection application uses the Intel® Distribution of OpenVINO™ toolkit to perform inference on an input video to locate people, safety vests, and hardhats within each frame.  We will setup, run, and view the results for this application for several different hardware devices (CPU. GPU, etc.) available on the compute nodes within the Intel® DevCloud for the Edge.  To accomplish this, we will be performing the following tasks:1. Use the [Model Optimizer](http://docs.openvinotoolkit.org/latest/_docs_MO_DG_Deep_Learning_Model_Optimizer_DevGuide.html) to create the model IR files in the necessary precisions2. Create the job file used to submit running inference on compute nodes3. Submit jobs for different compute nodes and monitor the job status until complete4. View results and assess performance  How it worksAt startup the safety gear detection application configures itself by parsing the command line arguments and reading the specified labels file.  Once configured, the application loads the specified inference model's IR files into the [Inference Engine](http://docs.openvinotoolkit.org/latest/_docs_IE_DG_Deep_Learning_Inference_Engine_DevGuide.html) and runs the three phases described in the following sections. Phase 1:  Pre-processingThe frames from the specified input video are read and pre-processed to have the frame data ready for input into inference.  Each frame is resized and its channels are transposed to match the input of the input requirements of the inference model.  The resulting blocks of frame data are written to the binary file `tmp/processed_vid.bin`. Phase 2:  InferenceThe binary file `tmp/processed_vid.bin` is read for input to inference to detect the specific objects: people, safety vests, and hardhats.  For each detected object within a frame, a message is written as a line to the output text file in the form:```          ```Where each field reports:-  - Frame number of results-  - Minimum x coordinate for restriction zone-  - Minimum y coordinate for restriction zone-  - Maximum x coordinate for restriction zone-  - Maximum y coordinate for restriction zone-  - The class identifier (integer) from the inference results -  - Detection label: "True" if safe, "False" if unsafe-  - Detection time taken to perform inference ("N/A" due to using Async API) Phase 3:  Post-processingAfter the safety gear detection application has finished running inference, a second executable is run to annotate the input video with the results from the output text file.  The final results is an output video with boxes drawn around detected objects with each box appearing with a label and probability value.In this sample, we provide three performance numbers for each architecture. However, they are not hard limits on the solution's performance. It is important to understand that for any application, you may want to combine preprocessing, inference, and post-processing, as opposed to separating them as done here. Combined preprocessing has several advantages:- If inference is run asynchronously on the accelerator, the rest of the system is available for parallel tasks for capturing input, preprocessing future frames, or post-processing past frames.- The inference application pipeline has better data locality, allowing for the reuse of data in caches such as in the application's memory or in the hard drive's cache. To run the application on the Intel® DevCloud for the Edge, a job is submitted to an edge compute node with a hardware accelerator such as Intel® HD Graphics GPU and Intel® Movidius™ Neural Compute Stick 2.  After inference on the input is completed, the output is stored in the appropriate `results//` directory.  The results are then viewed within this Jupyter* Notebook using the `videoHTML` video playback utility.The application and inference code for this sample is already implemented in the Python* files: - First pass, detection using inference: [`safety_gear_detection.py`](./safety_gear_detection.py)- Second pass, annotation using detection results: [`safety_gear_detection_annotate.py`](./safety_gear_detection_annotate.py)The following sections will guide you through configuring and running the safety gear detection application.  ConfigurationThe following sections describe all the necessary configuration to run the safety gear detection application. Command line argumentsThe first pass of the application is run from the command line using the following format:```bashpython3 safety_gear_detection.py ```The required command line __ to run the Python* executable [`safety_gear_detection.py`](./safety_gear_detection.py) are:- **-m** - Path to the _.xml_ IR file (created using [Model Optimizer](http://docs.openvinotoolkit.org/latest/_docs_MO_DG_Deep_Learning_Model_Optimizer_DevGuide.html)) for the inference model. - **-i** - Path to input video file- **--labels** - Path to labels file that matches the trained model used- **-o** - The path to where the output video file will be stored- **-d** - Device type to use to run inference (CPU, GPU, MYRIAD)- **-nreq** - The maximum number of requests to allow while using the Async APIThe second pass of the application to annotate video with results is run from the command line using the following format:```bashpython3 safety_gear_detection_annotate.py ```The required command line __ to run the application Python* executable [`safety_gear_detection_annotate.py`](./safety_gear_detection_annotate.py) are:- **-i** - Path to input video file- **-o** - The path to where the output video file will be stored.  Also used with environment variable `PBS_JOBID` to find output text file from application executable- **-f** - Output frame rate scale value (FPS=50.0/)- **-s** - Output resolution scale value to (input_w*,input_h*)   The labels fileIn order to label detected objects, the sample application requires a labels file associated with the model being used for detection.  The labels file is a text file containing all the classes/labels that the model can recognize, in the order that it was trained to recognize them (one class per line).  The included labels file `labels.txt`, is intended to be used with the specific `mobilenet-ssd` model that will be used for inference.Below are the contents of the `labels.txt` file that we will be using:```personvesthardhathardhat```  ImportsWe begin by importing all the Python* modules that will be used within this Jupyter* Notebook to run and display the results of the safety gear detection application on the Intel® DevCloud for the Edge:- [os](https://docs.python.org/3/library/os.htmlmodule-os) - Operating system specific module (used for file name parsing)- [time](https://docs.python.org/3/library/time.htmlmodule-time) - Time tracking module (used for measuring execution time)- [matplotlib.pyplot](https://matplotlib.org/) - pyplot is used for displaying output images- [sys](https://docs.python.org/3/library/sys.htmlmodule-sys) - System specific parameters and functions- [qarpo.demoutils](https://github.com/ColfaxResearch/qarpo) - Provides utilities for displaying results and managing jobs from within this Jupyter* NotebookRun the following cell to import the Python* dependencies needed.Tip: Select a cell and then use **Ctrl+Enter** to run that cell.<jupyter_code>import matplotlib.pyplot as plt
import os
import time
import sys
from qarpo.demoutils import *
from qarpo.model_visualizer_link import *
print('Imported Python modules successfully.')<jupyter_output><empty_output><jupyter_text>Create the IR files for the inference modelThe Intel® Distribution of OpenVINO™ toolkit includes the [Model Optimizer](http://docs.openvinotoolkit.org/latest/_docs_MO_DG_Deep_Learning_Model_Optimizer_DevGuide.html) used to convert and optimize trained models into the Intermediate Representation (IR) model files, and the [Inference Engine](http://docs.openvinotoolkit.org/latest/_docs_IE_DG_Deep_Learning_Inference_Engine_DevGuide.html) that uses the IR model files to run inference on hardware devices.  The IR model files can be created from trained models from popular frameworks (e.g. Caffe\*, Tensorflow*, etc.).  For this sample, the Caffe* model is supplied in the directory `/data/reference-sample-data/safety-gear-detection/` which contains the model files:- **worker_safety_mobilenet.prototxt** - The deployed [Protocol Buffer](https://developers.google.com/protocol-buffers) file that describes the network architecture to run inference- **worker_safety_mobilenet.caffemodel** - Binary containing trained weightsThese files will need to be optimized using the Model Optimizer to create the necessary IR files.  We will be running the inference model on different hardware devices which have different requirements on the precision of the model (see [Inference Engine Supported Model Formats](https://docs.openvinotoolkit.org/latest/_docs_IE_DG_supported_plugins_Supported_Devices.htmlsupported_model_formats) for details).  For our purposes, we will focus on the use of the two most common precisions, FP32 and FP16.For this model, we will run the Model Optimizer using the format:```bashmo.py \    --input_model  \    --model_name  \    --data_type  \    -o  ```The input arguments are as follows:- **--input_model** : The model's input *.caffemodel* file  (the *.prototxt* with the same base name will be automatically found, otherwise the `--input_proto` argument would need to be specified)- **--model_name** : Output model name to use- **--data_type** : The model's data type and precision (e.g. FP16, FP32, INT8, etc.)- **--o** : Output directory where to store the generated IR model filesFor converting our model, the complete command will look like the following:```bash!mo.py \    --input_model /data/reference-sample-data/safety-gear-detection/worker_safety_mobilenet.caffemodel \    --model_name mobilenet-ssd \    --data_type  \    -o models/mobilenet-ssd/```We will run the command twice, first with  set to `FP16` and then `FP32` to get all the IR files we will need to run inference on different devices.Note: More information on how to use Model Optimizer to convert Caffe* models may be found at:[Converting a Caffe* Model](https://docs.openvinotoolkit.org/latest/_docs_MO_DG_prepare_model_convert_model_Convert_Model_From_Caffe.html) Run the following cell to use the Model Optimizer to create the `FP16` and `FP32` model IR files:<jupyter_code># Create FP16 IR files
!mo.py \
--input_model /data/reference-sample-data/safety-gear-detection/worker_safety_mobilenet.caffemodel \
--model_name mobilenet-ssd \
--data_type FP16 \
-o models/mobilenet-ssd/FP16 

# Create FP32 IR files
!mo.py \
--input_model /data/reference-sample-data/safety-gear-detection/worker_safety_mobilenet.caffemodel \
--model_name mobilenet-ssd \
--data_type FP32 \
-o models/mobilenet-ssd/FP32

# find all resulting IR files
!echo "\nAll IR files that were created:"
!find ./models -name "*.xml" -o -name "*.bin"<jupyter_output><empty_output><jupyter_text>Tip: The '!' at the beginning of a line is a special Jupyter* Notebook command that allows you to run shell commands as if you are at a command line. The above command will also work in a terminal (with the '!' removed).As shown above from the output of the last `!find...` command, the required sets of IR model files (`*.xml` and `*.bin`) have been created.   To view a graph of the model used in this application, run the cell below then select the link generated:<jupyter_code>!ln -sfn /data data
showModelVisualizerLink("data/reference-sample-data/safety-gear-detection/worker_safety_mobilenet.caffemodel")<jupyter_output><empty_output><jupyter_text>Run inferenceThe following sections will go through the steps to run our inference application on the Intel® DevCloud for the Edge.   Configure inputFor convenience and consistency, in the next cell we set the Python* variable `InputVideo` to the input video file we will be using to run our sample application.  In addition, the variable `NumRequests_*` is set to maximum number of inference requests to make for each architecture while using the Async API.  The variables `NumRequests_*` are set accordingly to improve performance.  For example, `NumRequests_HDDLR` is set much higher than the rest for the [Intel® Vision Accelerator Design with Intel® Movidius™ VPUs](https://software.intel.com/openvino-toolkit/hardwareVPU) that has multiple VPUs and memory architecture which benefit significantly from launching multiple requests in parallel. Note: If you want to use a different input video, change the path in the following cell to the path of the video and run the cell again.  Also, if you want to change the number of inference requests, make the necessary change in the following cell and run the cell again.<jupyter_code># Set the path to the input video to use for the rest of this sample
InputVideo = "/data/reference-sample-data/safety-gear-detection/Safety_Full_Hat_and_Vest.mp4"
print(f"Input video file set to:{InputVideo}")

# Set maximum number of inference requests for CPU when using the Async API
NumRequests_CPU = 2
print(f"Number of inference requests for CPU set to:{NumRequests_CPU}")

# Set maximum number of inference requests for CPU when using the Async API
NumRequests_GPU = 4
print(f"Number of inference requests for GPU set to:{NumRequests_GPU}")

# Set maximum number of inference requests for NCS2 when using the Async API
NumRequests_NCS2 = 4
print(f"Number of inference requests for NCS2 set to:{NumRequests_NCS2}")

# Set maximum number of inference requests for HDDL-R when using the Async API
NumRequests_HDDLR = 128
print(f"Number of inference requests for HDDL-R set to:{NumRequests_HDDLR}")<jupyter_output><empty_output><jupyter_text>Optional exercise: View input without inferenceIf you are curious to see the input video, run the following cell to view the original video stream used for inference and this sample.<jupyter_code># create link and adjust video path to be able to display from /data using videoHTML()
!ln -sfn /data data
videoHTML('Safety Gear Video', ["."+InputVideo if InputVideo.startswith('/') else InputVideo])<jupyter_output><empty_output><jupyter_text>Optional adjustment of output video frame rate and sizeVideo rendering is performed by the separate Python* executable `object_detection_annotate.py` at the end of the job script. To reduce rendering time, you may reduce the output video quality using the `SCALE_FRAME_RATE` and `SCALE_RESOLUTION` variables. - Setting `SCALE_FRAME_RATE` to: - =1 writes all processed video frames with bounding boxes into the output video. This is the slowest option and it preserves all inferred data in the output video stream.   - =2 writes every other frame of the processed frames into the output video.  This scales the number of output video frames by half (1/2).- Setting `SCALE_RESOLUTION` to: - =1 produces the output video with the same resolution as the input video.  This is the slowest option. - <1 reduces the output video resolution. In the job script we have `SCALE_RESOLUTION=0.5` which sets the output video resolution in each dimension to 50% of the input video's resolution.Note: Changes to `SCALE_FRAME_RATE` or `SCALE_RESOLUTION` are made to the job file which appears in a later section and the job file must be written whenever changes are made.  Create the job fileWe will run inference on several different edge compute nodes present in the Intel® DevCloud for the Edge. We will send work to the edge compute nodes by submitting the corresponding non-interactive jobs into a queue. For each job, we will specify the type of the edge compute server that must be allocated for the job.The job file is a [Bash](https://www.gnu.org/software/bash/) script that serves as a wrapper around the Python* executable of our application that will be executed directly on the edge compute node.  One purpose of the job file is to simplify running an application on different compute nodes by accepting a few arguments and then performing accordingly any necessary steps before and after running the application executable.  For this sample, the job file we will be using is already written for you and appears in the next cell.  The job file will be submitted as if it were run from the command line using the following format:```bashsafety_gear_detection_job.sh     ```Where the job file input arguments are:-  - Output directory to use to store output files-  - Hardware device to use (e.g. CPU, GPU, etc.)-  - Which floating point precision inference model to use (FP32 or FP16)-  - Path to input video file-  - The maximum number of requests to allow while using the Async APIBased on the input arguments, the job file will do the following:- Change to the working directory `PBS_O_WORKDIR` where this Jupyter* Notebook and other files appear on the compute node- Create the - Choose the appropriate inference model IR file for the specified - Run the application Python* executable with the appropriate command line arguments- Run the application annotator Python* executable with the appropriate command line argumentsRun the following cell to create the `safety_gear_detection_job.sh` job file.  The [`%%writefile`](https://ipython.readthedocs.io/en/stable/interactive/magics.htmlcellmagic-writefile) line at the top will write the cell contents to the specified job file `safety_gear_detection_job.sh`.<jupyter_code>%%writefile safety_gear_detection_job.sh

# Store input arguments: <output_directory> <device> <fp_precision> <input_file> <num_reqs>
OUTPUT_FILE=$1
DEVICE=$2
FP_MODEL=$3
INPUT_FILE=$4
NUM_REQS=$5

# The default path for the job is the user's home directory,
#  change directory to where the files are.
cd $PBS_O_WORKDIR

# Make sure that the output directory exists.
mkdir -p $OUTPUT_FILE

# Set inference model IR files using specified precision
MODELPATH=models/mobilenet-ssd/${FP_MODEL}/mobilenet-ssd.xml
LABEL_FILE=/data/reference-sample-data/safety-gear-detection/labels.txt

# Run the safety gear detection code
python3 safety_gear_detection.py -m $MODELPATH \
                                 -i $INPUT_FILE \
                                 -o $OUTPUT_FILE \
                                 -d $DEVICE \
                                 -nireq $NUM_REQS \
                                 --labels $LABEL_FILE

# Run the output video annotator code
SCALE_FRAME_RATE=1    # scale number or output frames to input frames
SCALE_RESOLUTION=0.5  # scale output frame resolution 
python3 safety_gear_detection_annotate.py -i $INPUT_FILE \
                                          -o $OUTPUT_FILE \
                                          -f $SCALE_FRAME_RATE \
                                          -s $SCALE_RESOLUTION<jupyter_output><empty_output><jupyter_text>How to submit a jobNow that we have the job script, we can submit jobs to edge compute nodes in the Intel® DevCloud for the Edge.  To submit a job, the `qsub` command is used with the following format:```bashqsub  -N  -l  -F "" ```We can submit safety_gear_detection_job.sh to several different types of edge compute nodes simultaneously or just one node at a time.There are three options of `qsub` command that we use for this:-  - This is the job file we created in the previous step- `-N`  : Sets name specific to the job so that it is easier to distinguish  between it and other jobs- `-l`  - Specifies the number and the type of nodes using the format *nodes*=:[:...]- `-F` "" - String containing the input arguments described in the previous step to use when running the job file*(Optional)*: To see the available types of nodes on the Intel® DevCloud for the Edge, run the following cell.<jupyter_code>!pbsnodes | grep compnode | awk '{print $3}' | sort | uniq -c<jupyter_output><empty_output><jupyter_text>In the above output from executing the previous cell, the properties describe the node, and the number on the left is the number of available nodes of that architecture.  Submit jobsEach of the cells in the subsections below will submit a job to be run on different edge compute nodes. The output of each cell is the _JobID_ for the submitted job.  The _JobID_ can be used to track the status of the job.  After submission, a job will go into a waiting queue before running once the requested compute nodes become available.Note: You may submit all jobs at once or one at a time. Tip: **Shift+Enter** will run the cell and automatically move you to the next cell. This allows you to use **Shift+Enter** multiple times to quickly run through multiple cells, including markdown cells.  Submit to an edge compute node with an Intel® CPUIn the cell below, we submit a job to an edge node with an [Intel® Core™ i5-6500TE](https://ark.intel.com/products/88186/Intel-Core-i5-6500TE-Processor-6M-Cache-up-to-3-30-GHz.html) processor. The inference workload will run on the CPU.<jupyter_code>#Submit job to the queue
job_id_core = !qsub safety_gear_detection_job.sh -l nodes=1:idc001skl -F "results/core CPU FP32 {InputVideo} {NumRequests_CPU}" -N safety_gear_core
print(job_id_core[0])
#Progress indicators
if job_id_core:
    progressIndicator('results/core', 'pre_progress_'+job_id_core[0]+'.txt', "Preprocessing", 0, 100)
    progressIndicator('results/core', 'i_progress_'+job_id_core[0]+'.txt', "Inference", 0, 100)
    progressIndicator('results/core', 'post_progress_'+job_id_core[0]+'.txt', "Rendering", 0, 100)<jupyter_output><empty_output><jupyter_text>Submit to an edge compute node with Intel® Xeon® Gold 6258R CPUIn the cell below, we submit a job to an edge node with an [Intel® Xeon® Gold 6258R Processor](https://ark.intel.com/content/www/us/en/ark/products/199350/intel-xeon-gold-6258r-processor-38-5m-cache-2-70-ghz.html). The inference workload will run on the CPU.<jupyter_code>#Submit job to the queue
job_id_xeon_cascade_lake = !qsub safety_gear_detection_job.sh  -l nodes=1:idc018 -F "results/xeon_cascade_lake CPU FP32 {InputVideo} {NumRequests_CPU}" -N safety_gear_xeon_cascade_lake 
print(job_id_xeon_cascade_lake[0])
#Progress indicators
if job_id_xeon_cascade_lake:
    progressIndicator('results/xeon_cascade_lake', 'pre_progress_'+job_id_xeon_cascade_lake[0]+'.txt', "Preprocessing", 0, 100)
    progressIndicator('results/xeon_cascade_lake', 'i_progress_'+job_id_xeon_cascade_lake[0]+'.txt', "Inference", 0, 100)
    progressIndicator('results/xeon_cascade_lake', 'post_progress_'+job_id_xeon_cascade_lake[0]+'.txt', "Rendering", 0, 100)<jupyter_output><empty_output><jupyter_text>Submit to an edge compute node with Intel® Xeon® E3 1268L CPUIn the cell below, we submit a job to an edge node with an [Intel® Xeon® Processor E3-1268L v5](https://ark.intel.com/products/88178/Intel-Xeon-Processor-E3-1268L-v5-8M-Cache-2-40-GHz.html). The inference workload will run on the CPU.<jupyter_code>#Submit job to the queue
job_id_xeon_skylake = !qsub safety_gear_detection_job.sh  -l nodes=1:idc007xv5 -F "results/xeon_skylake CPU FP32 {InputVideo} {NumRequests_CPU}" -N safety_gear_xeon_skylake 
print(job_id_xeon_skylake[0])
#Progress indicators
if job_id_xeon_skylake:
    progressIndicator('results/xeon_skylake', 'pre_progress_'+job_id_xeon_skylake[0]+'.txt', "Preprocessing", 0, 100)
    progressIndicator('results/xeon_skylake', 'i_progress_'+job_id_xeon_skylake[0]+'.txt', "Inference", 0, 100)
    progressIndicator('results/xeon_skylake', 'post_progress_'+job_id_xeon_skylake[0]+'.txt', "Rendering", 0, 100)<jupyter_output><empty_output><jupyter_text>Submit to an edge compute node with Intel® Core CPU and using the integrated Intel® GPUIn the cell below, we submit a job to an edge node with an [Intel® Core i5-6500TE](https://ark.intel.com/products/88186/Intel-Core-i5-6500TE-Processor-6M-Cache-up-to-3-30-GHz.html). The inference workload will run on the Intel® HD Graphics 530 GPU integrated with the CPU.<jupyter_code>#Submit job to the queue
job_id_gpu = !qsub safety_gear_detection_job.sh -l nodes=1:idc001skl -F "results/gpu GPU FP32 {InputVideo} {NumRequests_GPU}" -N safety_gear_gpu 
print(job_id_gpu[0])
#Progress indicators
if job_id_gpu:
    progressIndicator('results/gpu', 'pre_progress_'+job_id_gpu[0]+'.txt', "Preprocessing", 0, 100)
    progressIndicator('results/gpu', 'i_progress_'+job_id_gpu[0]+'.txt', "Inference", 0, 100)
    progressIndicator('results/gpu', 'post_progress_'+job_id_gpu[0]+'.txt', "Rendering", 0, 100)<jupyter_output><empty_output><jupyter_text>Submit to an edge compute node with Intel® Neural Compute Stick 2In the cell below, we submit a job to an edge node with an [Intel Core i5-6500te](https://ark.intel.com/products/88186/Intel-Core-i5-6500TE-Processor-6M-Cache-up-to-3-30-GHz.html) CPU. The inference workload will run on an [Intel® Neural Compute Stick 2](https://software.intel.com/en-us/neural-compute-stick) installed in this node.<jupyter_code>#Submit job to the queue
job_id_ncs2 = !qsub safety_gear_detection_job.sh -l nodes=1:idc004nc2 -F "results/ncs2 MYRIAD FP16 {InputVideo} {NumRequests_NCS2}" -N safety_gear_ncs2
print(job_id_ncs2[0])
#Progress indicators
if job_id_ncs2:
    progressIndicator('results/ncs2', 'pre_progress_'+job_id_ncs2[0]+'.txt', "Preprocessing", 0, 100)
    progressIndicator('results/ncs2', 'i_progress_'+job_id_ncs2[0]+'.txt', "Inference", 0, 100)
    progressIndicator('results/ncs2', 'post_progress_'+job_id_ncs2[0]+'.txt', "Rendering", 0, 100)<jupyter_output><empty_output><jupyter_text>Submit to an edge compute node with Intel® Atom® and using the integrated Intel® GPUIn the cell below, we submit a job to an edge node with an [Intel® Atom® x7-E3950](https://ark.intel.com/products/96488/Intel-Atom-x7-E3950-Processor-2M-Cache-up-to-2-00-GHz.html) processor. The inference workload will run on the integrated Intel® HD Graphics 505 GPU.<jupyter_code>#Submit job to the queue
job_id_atom = !qsub safety_gear_detection_job.sh -l nodes=1:idc008u2g -F "results/atom GPU FP32 {InputVideo} {NumRequests_GPU}" -N safety_gear_atom
print(job_id_atom[0]) 
#Progress indicators
if job_id_atom:
    progressIndicator('results/atom', 'pre_progress_'+job_id_atom[0]+'.txt', "Preprocessing", 0, 100)
    progressIndicator('results/atom', 'i_progress_'+job_id_atom[0]+'.txt', "Inference", 0, 100)
    progressIndicator('results/atom', 'post_progress_'+job_id_atom[0]+'.txt', "Rendering", 0, 100)<jupyter_output><empty_output><jupyter_text>Submit to an edge compute node with Intel® Vision Accelerator Design with Intel® Movidius™ VPUsIn the cell below, we submit a job to an edge node with an [Intel Core i5-6500te CPU](https://ark.intel.com/products/88186/Intel-Core-i5-6500TE-Processor-6M-Cache-up-to-3-30-GHz.html). The inference workload will run on an [Intel® Vision Accelerator Design with Intel® Movidius™ VPUs](https://software.intel.com/openvino-toolkit/hardwareVPU) accelerator installed in this node that has eight VPUs.<jupyter_code>#Submit job to the queue
job_id_hddlr = !qsub safety_gear_detection_job.sh -l nodes=1:idc002mx8 -F "results/hddlr HDDL FP16 {InputVideo} {NumRequests_HDDLR}" -N safety_gear_hddlr
print(job_id_hddlr[0])
#Progress indicators
if job_id_hddlr:
    progressIndicator('results/hddlr', 'pre_progress_'+job_id_hddlr[0]+'.txt', "Preprocessing", 0, 100)
    progressIndicator('results/hddlr', 'i_progress_'+job_id_hddlr[0]+'.txt', "Inference", 0, 100)
    progressIndicator('results/hddlr', 'post_progress_'+job_id_hddlr[0]+'.txt', "Rendering", 0, 100)<jupyter_output><empty_output><jupyter_text>Monitor job statusTo check the status of the jobs that have been submitted, use the `qstat` command.  The custom Jupyter* Notebook widget `liveQstat()` is provided to display the output of `qstat` with live updates.  Run the following cell to display the current job status with periodic updates.<jupyter_code>liveQstat()<jupyter_output><empty_output><jupyter_text>You should see the jobs that you have submitted (referenced by the `JobID` that gets displayed right after you submit the jobs in the previous step).There should also be an extra job in the queue named `jupyterhub-singleuser`: this job is your current Jupyter* Notebook session which is always running.The `S` column shows the current status of each job: - If the status is `Q`, then the job is queued and waiting for available resources- If ste status is `R`, then the job is running- If the job is no longer listed, then the job has completedNote: The amount of time spent in the queue depends on the number of users accessing the requested compute nodes. Once the jobs for this sample application begin to run, they should take from 1 to 5 minutes each to complete. Wait!: Please wait for the inference jobs and video rendering to complete before proceeding to the next step to view results. View resultsOnce the jobs have completed, the queue system outputs the stdout and stderr streams of each job into files with names of the forms .o and .e, respecitvely.  The *JobName* corresponds to the `-N` option when submitting the job using the `qsub` command.  The output video file for each job is written to the file `output.mp4` located in the directory `results/` that was specified as the output directory to the job file.  We will now use the `videoHTML()` utility to display the output video files within this Jupyter* notebook.  Calling `videoHTML()` from a Python* cell follows the form:```pythonvideoHTML(title, [list_of_video_files], statistics(optional))```The parameters are:- *title* - Title to put at the top of the displayed output- \[*list_of_video_files*\] - Python* list of video files to display- *statistics(optional)* - Optional statistics file containing the number of seconds it took to process a number of framesRun the cells below to display the videos.  View results from an Intel® CPU<jupyter_code>videoHTML('Intel Core CPU', 
          [f'results/core/output_{job_id_core[0]}.mp4'],f'results/core/stats_{job_id_core[0]}.txt')<jupyter_output><empty_output><jupyter_text>View results from an Intel® Xeon® Gold 6825R CPU<jupyter_code>videoHTML('Intel Xeon Cascade Lake CPU',
          [f'results/xeon_cascade_lake/output_{job_id_xeon_cascade_lake[0]}.mp4'],
          f'results/xeon_cascade_lake/stats_{job_id_xeon_cascade_lake[0]}.txt')<jupyter_output><empty_output><jupyter_text>View results from an Intel® Xeon® E3-1268L V5 CPU<jupyter_code>videoHTML('Intel Xeon Skylake CPU',
          [f'results/xeon_skylake/output_{job_id_xeon_skylake[0]}.mp4'],
          f'results/xeon_skylake/stats_{job_id_xeon_skylake[0]}.txt')<jupyter_output><empty_output><jupyter_text>View results from an Intel® Core CPU and integrated Intel® GPU<jupyter_code>videoHTML('Intel Core + Intel GPU',
          [f'results/gpu/output_{job_id_gpu[0]}.mp4'],f'results/gpu/stats_{job_id_gpu[0]}.txt')<jupyter_output><empty_output><jupyter_text>View results from an Intel® Neural Compute Stick 2<jupyter_code>videoHTML('Intel CPU + Intel NCS2', 
          [f'results/ncs2/output_{job_id_ncs2[0]}.mp4'],f'results/ncs2/stats_{job_id_ncs2[0]}.txt')<jupyter_output><empty_output><jupyter_text>View results from an Intel® Atom® and integrated Intel® GPU<jupyter_code>videoHTML('Intel Atom CPU + Intel GPU',
          [f'results/atom/output_{job_id_atom[0]}.mp4'],f'results/atom/stats_{job_id_atom[0]}.txt')<jupyter_output><empty_output><jupyter_text>View results from Intel® Vision Accelerator Design with Intel® Movidius™ VPUs<jupyter_code>videoHTML('Intel VPU HDDL-R',
          [f'results/hddlr/output_{job_id_hddlr[0]}.mp4'],f'results/hddlr/stats_{job_id_hddlr[0]}.txt')<jupyter_output><empty_output><jupyter_text>View and assess performance resultsThe running time of each inference task is recorded in `results//stats.txt`. Run the cell below to plot the results of all jobs side-by-side. Lower values mean better performance for **Inference Engine Processing Time** and higher values mean better performance for **Inference Engine FPS**. When comparing results, please keep in mind that some architectures are optimized for highest performance, others for low power or other metrics.<jupyter_code># Create table of <architecture>, <title> for plotting
arch_list = [('core', 'Intel Core\ni5-6500TE\nCPU'),
             ('xeon_cascade_lake', 'Intel Xeon\nGold\n 6258R\nCPU'),
             ('xeon_skylake', 'Intel Xeon\nE3-1268L v5\nCPU'),
             ('gpu', ' Intel Core\ni5-6500TE\nHD530/GPU'),
             ('ncs2', 'Intel VPU\ni5-6500TE\nNCS2 VPU'),
             ('atom', 'Intel Atom\nx7-E3950\nHD505/GPU'),
             ('hddlr', 'Intel VPU\n8xVPU\nHDDL-R')]
# For each archtecture in table, create path to stats file or placeholder 
stats_list = []
for arch, a_name in arch_list:
    # if job_id_<architecture> exists, the job was run and has a stats file
    if 'job_id_'+arch in vars():
        stats_list.append((f'results/{arch}/stats_{vars()["job_id_"+arch][0]}.txt', a_name))
    else:
        stats_list.append(('placeholder'+arch, a_name))
# Plot the execution time from the stats files
summaryPlot(stats_list, 'Architecture', 'Time, seconds', 'Inference Engine Processing Time', 'time')
# Plot the frames per second from the stats files
summaryPlot(stats_list, 'Architecture', 'Frames per second', 'Inference Engine FPS', 'fps')<jupyter_output><empty_output><jupyter_text>Telemetry DashboardOnce your submitted jobs are completed, run the cells below to view telemetry dashboards containing performance metrics for your model and target architecture.<jupyter_code>link_t = "<a target='_blank' href='{href}'> Click here to view telemetry dashboard of the last job ran on Intel® Core™ i5-6500TE</a>"

result_file = "https://devcloud.intel.com/edge/metrics/d/" + job_id_core[0].split('.')[0]

html = HTML(link_t.format(href=result_file))

display(html)
link_t = "<a target='_blank' href='{href}'> Click here to view metering dashboard of the last job ran on Intel® Xeon® Gold 6258R CPU</a>"

result_file = "https://devcloud.intel.com/edge/metrics/d/" + job_id_xeon_cascade_lake[0].split('.')[0]

html = HTML(link_t.format(href=result_file))

display(html)
link_t = "<a target='_blank' href='{href}'> Click here to view metering dashboard of the last job ran on Intel® Xeon® E3-1268L v5 CPU</a>"

result_file = "https://devcloud.intel.com/edge/metrics/d/" + job_id_xeon_skylake[0].split('.')[0]

html = HTML(link_t.format(href=result_file))

display(html)
link_t = "<a target='_blank' href='{href}'> Click here to view metering dashboard of the last job ran on Intel® Core CPU and using the onboard Intel® GPU</a>"

result_file = "https://devcloud.intel.com/edge/metrics/d/" + job_id_gpu[0].split('.')[0]

html = HTML(link_t.format(href=result_file))

display(html)
link_t = "<a target='_blank' href='{href}'> Click here to view metering dashboard of the last job ran on IEI Mustang-V100-MX8 ( Intel® Movidius™ Myriad™ X Vision Processing Unit (VPU))</a>"

result_file = "https://devcloud.intel.com/edge/metrics/d/" + job_id_hddlr[0].split('.')[0]

html = HTML(link_t.format(href=result_file))

display(html)
link_t = "<a target='_blank' href='{href}'> Click here to view metering dashboard of the last job ran on Intel® NCS 2 (Neural Compute Stick 2)</a>"

result_file = "https://devcloud.intel.com/edge/metrics/d/" + job_id_ncs2[0].split('.')[0]

html = HTML(link_t.format(href=result_file))

display(html)
link_t = "<a target='_blank' href='{href}'> Click here to view metering dashboard of the last job ran on UP Squared Grove IoT Development Kit (UP2)</a>"

result_file = "https://devcloud.intel.com/edge/metrics/d/" + job_id_atom[0].split('.')[0]

html = HTML(link_t.format(href=result_file))

display(html)<jupyter_output><empty_output>
{'fraction_non_alphanumeric': 0.08694992028747121, 'fraction_numerical': 0.013209504770098945, 'mean_word_length': 5.003038128512836, 'pattern_counts': {'":': 0, '<': 120, '<?xml version=': 0, '>': 119, 'https://': 33, 'lorem ipsum': 0, 'www.': 2, 'xml': 4}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 15, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'chain_length': '24', 'dir': 'jupyter-structured-clean-dedup', 'id': '249396', 'license': 'MIT', 'n_tokens_mistral': 11943, 'n_tokens_neox': 11320, 'n_words': 4461, 'path': 'app/safety_gear_detection.ipynb', 'repo_name': 'Akash671/Intel', 'size': '39517'}