pip install onnxruntime # CPU engine★The inference engine. Python 3.11–3.14. Ships CPU + (on the GPU build) other providers.pip install onnxruntime-gpu # CUDA/TensorRT build★GPU wheel (Linux/Windows). Don't install both CPU and GPU packages in the same env.pip install onnx # format/graph toolkitOnly needed to build/inspect/edit graphs or run the checker/shape-inference (cards 9–10). Not required just to run a model.import onnxruntime as ort · import onnxConventional aliases.ort.__version__/onnx.__version__to confirm what's installed.
sess = ort.InferenceSession("model.onnx", providers=["CPUExecutionProvider"])★The core object: loads & compiles the model. Always passproviders=explicitly (see card 6).outs = sess.run(None, {"input": x})★Run inference. First arg = list of output names (None= all); second ={input_name: numpy_array}. Returns a list of numpy arrays.outs = sess.run(["logits"], {"input": x, "mask": m})Request specific outputs by name; feed multiple inputs. Inputs must be numpy arrays of the right dtype/shape.# dtype mismatch -> "unexpected input data type" errorgotchaMatch the model's dtype exactly, e.g.x.astype(np.float32). int64 vs int32 and float32 vs float64 are common culprits.
for i in sess.get_inputs(): print(i.name, i.shape, i.type)★Discover expected names/shapes/dtypes.sess.get_outputs()for outputs. Dynamic dims show as strings (e.g.'batch').name = sess.get_inputs()[0].name sess.run(None, {name: x})Grab the input name programmatically instead of hardcoding it.io = sess.io_binding() io.bind_input(...); io.bind_output(...); sess.run_with_iobinding(io)IO binding keeps tensors on-device (GPU) across calls — avoids host↔device copies for max throughput.ort.OrtValue.ortvalue_from_numpy(x, "cuda", 0)Create device-resident tensors to bind directly.