---
title: QkTarget (latest version)
description: API reference for QkTarget in the latest version of qiskit-c
source: https://quantum.cloud.ibm.com/docs/en/api/qiskit-c/qk-target
---

# QkTarget

```c
typedef struct QkTarget QkTarget
```

A mapping of instructions and properties representing the particular constraints of a backend. Its purpose is to provide the compiler with information that allows it to compile an input circuit into another that is optimized taking in consideration the `QkTarget`’s specifications. This structure represents a low level interface to the main Target data structure in Rust, which represents the base class for its Python counterpart, [`Target`](/docs/api/qiskit/qiskit.transpiler.Target#qiskit.transpiler.Target "qiskit.transpiler.Target").

Here’s an example of how this structure works:

```c
#include <qiskit.h>
#include <math.h>

// Create a Target with 2 qubits
QkTarget *target = qk_target_new(2);
// Create an entry for a CX Gate with qargs (0, 1) and properties
// duration = 0.0123
// error = NaN
uint32_t qargs[2] = {0, 1};
QkTargetEntry *entry = qk_target_entry_new(QkGate_CX);
qk_target_entry_add_property(entry, qargs, 2, 0.0123, NAN);

// Add a CX Gate to the target
qk_target_add_instruction(target, entry);

// Add a global H gate
qk_target_add_instruction(target, qk_target_entry_new(QkGate_H));

// Free the created target.
qk_target_free(target);
```

The Target C API currently only supports additions of `QkGate` instances with either no parameters or fixed parameters. Support for regular parameters will be added in the future. The functionality will keep expanding over time as we improve our Rust data model capabilities.

## Data Types

### QkInstructionProperties

`struct QkInstructionProperties`

A representation of a Target operation’s instruction properties.

#### double duration

The duration, in seconds, of the instruction on the specified set of qubits. Will be set to `NaN` if the property is not defined.

#### double error

The average error rate for the instruction on the specified set of qubits. Will be set to `NaN` if the property is not defined.

### QkTargetOp

`struct QkTargetOp`

Representation of an operation identified within the Target.

This struct is created natively by the underlying `Target` API and users should not write to it directly nor try to free its attributes manually as it would lead to undefined behavior. To free this struct, users should call `qk_target_op_clear` instead.

#### QkOperationKind op\_type

The identifier for the current operation.

#### char \*name

The name of the operation.

#### uint32\_t num\_qubits

The number of qubits this operation supports. Will default to `(uint32_t)-1` in the case of a variadic.

#### const QkParam \*\*params

The parameters tied to this operation, as `QkParam`. If there are no parameters then this value will be represented with a `NULL` pointer.

#### uint32\_t num\_params

The number of parameters supported by this operation. Will default to `(uint32_t)-1` in the case of a variadic.

## Functions

### qk\_target\_new

`QkTarget *qk_target_new(uint32_t num_qubits)`

Construct a new `QkTarget` with the given number of qubits. The number of qubits is bound to change if an instruction is added with properties that apply to a collection of qargs in which any index is higher than the specified number of qubits

#### Example

```c
QkTarget *target = qk_target_new(5);
```

**Parameters**

- **num\_qubits** – The number of qubits the `QkTarget` will explicitly support.

**Returns**

A pointer to the new `QkTarget`

### qk\_target\_borrow\_from\_python

`QkTarget *qk_target_borrow_from_python(PyObject *ob)`

Retrieve a `QkTarget` pointer from a Python object.

This borrows a Python reference and extracts the `QkTarget` pointer for it, if it is of the correct type. The returned pointer is borrowed from the `ob` pointer. If the `PyObject` is not the correct type, the return value is `NULL` and the exception state of the Python interpreter is set.

You must be attached to a Python interpreter to call this function.

You can also use `qk_target_convert_from_python`, which is logically the exact same as this function, but can be directly used as a “converter” function for the `PyArg_Parse*` family of Python converter functions.

#### Safety

The caller must be attached to a Python interpreter. Behavior is undefined if `ob` is not a valid non-null pointer to a Python object.

**Parameters**

- **ob** – A borrowed Python object.

**Returns**

A pointer to the native object, or `NULL` if the Python object is the wrong type.

### qk\_target\_convert\_from\_python

`int qk_target_convert_from_python(PyObject *object, void *address)`

Retrieve a Target pointer from a Python object.

This borrows a Python reference and extracts the `QkTarget` pointer for it into `address`, if it is of the correct type. The returned pointer is borrowed from the `object` pointer. If the `PyObject` is not the correct type, the return value is 1, the exception state of the Python interpreter is set, and `address` is unchanged.

You must be attached to a Python interpreter to call this function.

You can also use `qk_target_borrow_from_python`, which is logically the exact same as this, but with a more natural signature for direct usage.

#### Safety

The caller must be attached to a Python interpreter. Behavior is undefined if `object` is not a valid non-null pointer to a Python object, or if `address` is not a pointer to writeable data of the correct type.

**Parameters**

- **object** – A borrowed Python object.
- **address** – The location to write the output to.

**Returns**

1 on success, 0 on failure.

### qk\_target\_num\_qubits

`uint32_t qk_target_num_qubits(const QkTarget *target)`

Returns the number of qubits of this `QkTarget`.

#### Example

```c
QkTarget *target = qk_target_new(5);
uint32_t num_qubits = qk_target_num_qubits(target);
```

#### Safety

Behavior is undefined if `QkTarget` is not a valid, non-null pointer to a `QkTarget`.

**Parameters**

- **target** – A pointer to the `QkTarget`.

**Returns**

The number of qubits this target can use.

### qk\_target\_dt

`double qk_target_dt(const QkTarget *target)`

Returns the dt value of this `QkTarget`.

#### Example

```c
QkTarget *target = qk_target_new(5);
qk_target_set_dt(target, 10e-9);
double dt = qk_target_dt(target);
```

#### Safety

Behavior is undefined if `QkTarget` is not a valid, non-null pointer to a `QkTarget`.

**Parameters**

- **target** – A pointer to the `QkTarget`.

**Returns**

The dt value of this `QkTarget` or `NAN` if not assigned.

### qk\_target\_granularity

`uint32_t qk_target_granularity(const QkTarget *target)`

Returns the granularity value of this `QkTarget`.

#### Example

```c
QkTarget *target = qk_target_new(5);
// The value defaults to 1
uint32_t granularity = qk_target_granularity(target);
```

#### Safety

Behavior is undefined if `QkTarget` is not a valid, non-null pointer to a `QkTarget`.

**Parameters**

- **target** – A pointer to the `QkTarget`.

**Returns**

The `granularity` value of this `QkTarget`.

### qk\_target\_min\_length

`uint32_t qk_target_min_length(const QkTarget *target)`

Returns the `min_length` value of this `QkTarget`.

#### Example

```c
QkTarget *target = qk_target_new(5);
// The value defaults to 1
size_t min_length = qk_target_min_length(target);
```

#### Safety

Behavior is undefined if `QkTarget` is not a valid, non-null pointer to a `QkTarget`.

**Parameters**

- **target** – A pointer to the `QkTarget`.

**Returns**

The `min_length` value of this `QkTarget`.

### qk\_target\_pulse\_alignment

`uint32_t qk_target_pulse_alignment(const QkTarget *target)`

Returns the `pulse_alignment` value of this `QkTarget`.

#### Example

```c
QkTarget *target = qk_target_new(5);
// The value defaults to 1
uint32_t pulse_alignment = qk_target_pulse_alignment(target);
```

#### Safety

Behavior is undefined if `QkTarget` is not a valid, non-null pointer to a `QkTarget`.

**Parameters**

- **target** – A pointer to the `QkTarget`.

**Returns**

The `pulse_alignment` value of this `QkTarget`.

### qk\_target\_acquire\_alignment

`uint32_t qk_target_acquire_alignment(const QkTarget *target)`

Returns the `acquire_alignment` value of this `QkTarget`.

#### Example

```c
QkTarget *target = qk_target_new(5);
// The value defaults to 0
uint32_t acquire_alignment = qk_target_pulse_alignment(target);
```

#### Safety

Behavior is undefined if `QkTarget` is not a valid, non-null pointer to a `QkTarget`.

**Parameters**

- **target** – A pointer to the `QkTarget`.

**Returns**

The `acquire_alignment` value of this `QkTarget`.

### qk\_target\_set\_dt

`QkExitCode qk_target_set_dt(QkTarget *target, double dt)`

Sets the dt value of this `QkTarget`.

#### Example

```c
QkTarget *target = qk_target_new(5);
double dt = qk_target_set_dt(target, 10e-9);
```

#### Safety

Behavior is undefined if `QkTarget` is not a valid, non-null pointer to a `QkTarget`.

**Parameters**

- **target** – A pointer to the `QkTarget`.
- **dt** – The `dt` value for the system time resolution of input.

**Returns**

`QkExitCode` specifying if the operation was successful.

### qk\_target\_set\_granularity

`QkExitCode qk_target_set_granularity(QkTarget *target, uint32_t granularity)`

Sets the `granularity` value of this `QkTarget`.

#### Example

```c
QkTarget *target = qk_target_new(5);
// The value defaults to 1
qk_target_set_granularity(target, 2);
```

#### Safety

Behavior is undefined if `QkTarget` is not a valid, non-null pointer to a `QkTarget`.

**Parameters**

- **target** – A pointer to the `QkTarget`.
- **granularity** – The value for the minimum pulse gate resolution in units of `dt`.

**Returns**

`QkExitCode` specifying if the operation was successful.

### qk\_target\_set\_min\_length

`QkExitCode qk_target_set_min_length(QkTarget *target, uint32_t min_length)`

Sets the `min_length` value of this `QkTarget`.

#### Example

```c
QkTarget *target = qk_target_new(5);
// The value defaults to 1
qk_target_set_min_length(target, 3);
```

#### Safety

Behavior is undefined if `QkTarget` is not a valid, non-null pointer to a `QkTarget`.

**Parameters**

- **target** – A pointer to the `QkTarget`.
- **min\_length** – The minimum pulse gate length value in units of `dt`.

**Returns**

`QkExitCode` specifying if the operation was successful.

### qk\_target\_set\_pulse\_alignment

`QkExitCode qk_target_set_pulse_alignment(QkTarget *target, uint32_t pulse_alignment)`

Returns the `pulse_alignment` value of this `QkTarget`.

#### Example

```c
QkTarget *target = qk_target_new(5);
// The value defaults to 1
qk_target_set_pulse_alignment(target, 4);
```

#### Safety

Behavior is undefined if `QkTarget` is not a valid, non-null pointer to a `QkTarget`.

**Parameters**

- **target** – A pointer to the `QkTarget`.
- **pulse\_alignment** – value representing a time resolution of gate.

**Returns**

`QkExitCode` specifying if the operation was successful.

### qk\_target\_set\_acquire\_alignment

`QkExitCode qk_target_set_acquire_alignment(QkTarget *target, uint32_t acquire_alignment)`

Sets the `acquire_alignment` value of this `QkTarget`.

#### Example

```c
QkTarget *target = qk_target_new(5);
// The value defaults to 0
qk_target_set_acquire_alignment(target, 5);
```

#### Safety

Behavior is undefined if `QkTarget` is not a valid, non-null pointer to a `QkTarget`.

**Parameters**

- **target** – A pointer to the `QkTarget`.
- **acquire\_alignment** – value representing a time resolution of measure instruction starting time.

**Returns**

`QkExitCode` specifying if the operation was successful.

### qk\_target\_copy

`QkTarget *qk_target_copy(QkTarget *target)`

Creates a copy of the `QkTarget`.

#### Example

```c
QkTarget *target = qk_target_new(5);
QkTargetEntry *entry = qk_target_entry_new(QkGate_CX);
uint32_t qargs[2] = {0, 1};
qk_target_entry_add_property(entry, qargs, 2, 0.0, 0.1);
QkExitCode result = qk_target_add_instruction(target, entry);

QkTarget *copied = qk_target_copy(target);
```

#### Safety

Behavior is undefined if `QkTarget` is not a valid, non-null pointer to a `QkTarget`.

**Parameters**

- **target** – A pointer to the `QkTarget` to copy.

**Returns**

A pointer to the new copy of the `QkTarget`.

### qk\_target\_free

`void qk_target_free(QkTarget *target)`

Free the `QkTarget`.

#### Example

```c
QkTarget *target = qk_target_new(5);
qk_target_free(target);
```

#### Safety

Behavior is undefined if `QkTarget` is not a valid, non-null pointer to a `QkTarget`.

**Parameters**

- **target** – A pointer to the `QkTarget` to free.

### qk\_target\_add\_instruction

`QkExitCode qk_target_add_instruction(QkTarget *target, QkTargetEntry *target_entry)`

Adds a gate to the `QkTarget` through a `QkTargetEntry`.

#### Example

```c
QkTarget *target = qk_target_new(5);
QkTargetEntry *entry = qk_target_entry_new(QkGate_CX);
uint32_t qargs[2] = {0, 1};
qk_target_entry_add_property(entry, qargs, 2, 0.0, 0.1);
QkExitCode result = qk_target_add_instruction(target, entry);
```

#### Safety

Behavior is undefined if `QkTarget` is not a valid, non-null pointer to a `QkTarget`.

Behavior is undefined if `entry` is not a valid, non-null pointer to a `QkTargetEntry`.

**Parameters**

- **target** – A pointer to the `QkTarget`.
- **target\_entry** – A pointer to the `QkTargetEntry`. The pointer gets freed when added to the `QkTarget`.

**Returns**

`QkExitCode` specifying if the operation was successful.

### qk\_target\_update\_property

`QkExitCode qk_target_update_property(QkTarget *target, QkGate instruction, uint32_t *qargs, uint32_t num_qubits, double duration, double error)`

Modifies the properties of a gate in the `QkTarget`.

#### Example

```c
QkTarget *target = qk_target_new(5);
double params[1] = {3.1415};
QkTargetEntry *entry = qk_target_entry_new_fixed(QkGate_CRX, params, "crx_pi");
uint32_t qargs[2] = {0, 1};
qk_target_entry_add_property(entry, qargs, 2, 0.0, 0.1);
qk_target_add_instruction(target, entry);

qk_target_update_property(target, QkGate_CRX, qargs, 2, 0.0012, 1.1);
```

#### Safety

Behavior is undefined if `QkTarget` is not a valid, non-null pointer to a `QkTarget`.

The `qargs` type is expected to be a pointer to an array of `uint32_t` where the length matches is specified by `num_qubits` and has to match the expectation of the gate. If the array is insufficiently long the behavior of this function is undefined as this will read outside the bounds of the array. It can be a null pointer if there are no qubits for a given gate. You can check `qk_gate_num_qubits` to determine how many qubits are required for a given gate.

**Parameters**

- **target** – A pointer to the `QkTarget`.
- **instruction** – The instruction to modify.
- **qargs** – The pointer to the array of `uint32_t` values to use as qargs. Can be `NULL` if global.
- **num\_qubits** – The number of qubits of the instruction..
- **duration** – The instruction’s duration in seconds on the specific set of qubits.
- **error** – The instruction’s average error rate on the specific set of qubits.

**Returns**

`QkExitCode` specifying if the operation was successful.

### qk\_target\_num\_instructions

`size_t qk_target_num_instructions(const QkTarget *target)`

Returns the number of instructions tracked by a `QkTarget`.

#### Example

```c
QkTarget *target = qk_target_new(5);
QkTargetEntry *target_entry = qk_target_entry_new(QkGate_H);
qk_target_add_instruction(target, target_entry);

size_t num_instructions = qk_target_num_instructions(target);
```

#### Safety

Behavior is undefined if `QkTarget` is not a valid, non-null pointer to a `QkTarget`.

**Parameters**

- **target** – A pointer to the `QkTarget`.

**Returns**

The length of the target.

### qk\_target\_instruction\_supported

`bool qk_target_instruction_supported(const QkTarget *target, const char *operation_name, const uint32_t *qargs, QkParam **params)`

Checks if the provided instruction and its qargs are supported by this `Target`.

#### Example

```c
// Create a mock target with only a global crx entry
// and 3.14 as its rotation parameter.
QkTarget *target = qk_target_new(5);
QkTargetEntry *crx_entry = qk_target_entry_new_fixed(QkGate_CRX, (double[]){3.14});
qk_target_entry_add_property(crx_entry, NULL, 0, 0.0, 0.1);
qk_target_add_instruction(target, crx_entry);

// Check if target is compatible with a "crx" gate
// at [0, 1] with 3.14 rotation.
QkParam *params[1] = {qk_param_from_double(3.14)};
qk_target_instruction_supported(target, "crx", (uint32_t []){0, 1}, params);

// Free the pointers
qk_param_free(params[0]);
qk_target_free(target);
```

#### Safety

Behavior is undefined if `target` is not a valid, non-null pointer to a `QkTarget`.

The `qargs` argument is expected to be a pointer to an array of `u32int_t` where the length matches the expectation of the gate. If the array is insufficiently long the behavior of this function is undefined as this will read outside the bounds of the array. It can be a null pointer if there are no qubits for a given gate. You can check `qk_gate_num_qubits` to determine how many qubits are required for a given gate.

The `params` argument is expected to be an array of `QkParam` where the length matches the expectation of the operation in question. If the array is insufficiently long, the behavior will be undefined just as mentioned above for the `qargs` argument. You can always check `qk_gate_num_params` in the case of a `QkGate`.

**Parameters**

- **target** – A pointer to the `Target`.
- **operation\_name** – The instruction name to check for.
- **qargs** – The pointer to the array of `uint32_t` values to use as qargs. Can be `NULL` if global.
- **params** – A pointer to an array of pointers of `QkParam` objects as parameters to check. Can be `NULL` if no parameters are present.

**Returns**

Whether the instruction is supported or not.

### qk\_target\_op\_index

`size_t qk_target_op_index(const QkTarget *target, const char *name)`

Return the index at which an operation is located based on its name.

#### Example

```c
QkTarget *target = qk_target_new(5);
QkTargetEntry *target_entry = qk_target_entry_new(QkGate_H);
qk_target_add_instruction(target, target_entry);

size_t op_idx = qk_target_op_index(target, "h");
```

#### Safety

Behavior is undefined if `QkTarget` is not a valid, non-null pointer to a `QkTarget`. Behavior is undefined if `name` is not a pointer to a valid null-terminated string.

**Parameters**

- **target** – A pointer to the `QkTarget`.
- **name** – The name to get the index of.

**Returns**

the index in which the operation is the maximum value of `size_t` in the case it is not in the Target.

### qk\_target\_op\_name

`char *qk_target_op_name(const QkTarget *target, size_t index)`

Return the name of the operation stored at that index in the `QkTarget` instance’s gate map.

#### Example

```c
QkTarget *target = qk_target_new(5);
QkTargetEntry *target_entry = qk_target_entry_new(QkGate_H);
qk_target_add_instruction(target, target_entry);

char *op_name = qk_target_op_name(target, 0);
// Free after use
qk_str_free(op_name);
```

#### Safety

Behavior is undefined if `QkTarget` is not a valid, non-null pointer to a `QkTarget`.

**Parameters**

- **target** – A pointer to the `QkTarget`.
- **index** – The index at which the gate is stored.

**Returns**

The name of the operation associated with the provided index.

### qk\_target\_op\_num\_properties

`size_t qk_target_op_num_properties(const QkTarget *target, size_t index)`

Return the number of properties defined for the specified operation in the `QkTarget` instance, a.k.a. the length of the property map. Panics if the operation index is not present.

#### Example

```c
QkTarget *target = qk_target_new(5);
QkTargetEntry *target_entry = qk_target_entry_new(QkGate_H);
qk_target_add_instruction(target, target_entry);

size_t num_props = qk_target_op_num_properties(target, 0);
```

#### Safety

Behavior is undefined if `QkTarget` is not a valid, non-null pointer to a `QkTarget`.

**Parameters**

- **target** – A pointer to the `QkTarget`.
- **index** – The index in which the gate is stored.

**Returns**

The number of properties specified for the operation associated with that index.

### qk\_target\_op\_qargs\_index

`size_t qk_target_op_qargs_index(const QkTarget *target, size_t op_idx, const uint32_t *qargs)`

Retrieve the index at which some qargs are stored. Returns `SIZE_MAX` if not found.

#### Example

```c
QkTarget *target = qk_target_new(5);

QkTargetEntry *entry = qk_target_entry_new(QkGate_CX);
uint32_t qargs[2] = {0, 1};
qk_target_entry_add_property(entry, qargs, 2, 0.0, 0.1);
qk_target_add_instruction(target, entry);

size_t idx_0_1 = qk_target_op_qargs_index(target, 0, qargs);
```

#### Safety

Behavior is undefined if `QkTarget` is not a valid, non-null pointer to a `QkTarget`.

**Parameters**

- **target** – A pointer to the `QkTarget`.
- **op\_idx** – The index at which the operation is stored.
- **qargs** – A pointer to the array of `uint32_t` qubit indices to check for, can be a null pointer to check for global properties.

**Returns**

The index of the qargs associated with the instruction at the specified `op_idx` index or `SIZE_MAX` if the qargs are not present.

### qk\_target\_op\_qargs

`void qk_target_op_qargs(const QkTarget *target, size_t op_idx, size_t qarg_idx, uint32_t **qargs_out, uint32_t *qargs_len)`

Retrieve the qargs for the operation by index.

Panics if any of the indices are out of range.

#### Example

```c
QkTarget *target = qk_target_new(5);

QkTargetEntry *entry = qk_target_entry_new(QkGate_CX);
uint32_t qargs[2] = {0, 1};
qk_target_entry_add_property(entry, qargs, 2, 0.0, 0.1);
qk_target_add_instruction(target, entry);

uint32_t *qargs_retrieved;
uint32_t qargs_length;
qk_target_op_qargs(target, 0, 0, &qargs_retrieved, &qargs_length);
if (qargs_retrieved) {
    // We should enter this branch.
    printf("Number of qargs: %lu\n", qargs_length);
} else {
    printf("Qargs are global\n");
}
```

#### Safety

Behavior is undefined if `target` is not a valid, non-null pointer to a `QkTarget`. Behavior is undefined if each `qargs_out` or `qargs_len` are not aligned and writeable for a single value of the correct type.

**Parameters**

- **target** – A pointer to the `QkTarget`.
- **op\_idx** – The index at which the gate is stored.
- **qarg\_idx** – The index at which the qargs are stored.
- **qargs\_out** – An out pointer to an array qubits. If `op_idx` refers to a a global operation, a null pointer will be written. The written pointer is borrowed from the target and must not be freed. A zero-qargs instruction will write out a non-null pointer, though one that is invalid for reads.
- **qargs\_len** – An out pointer to the length of the qargs in `qargs_out`. If the index is global, the written length is not defined.

### qk\_target\_op\_props

`void qk_target_op_props(const QkTarget *target, size_t op_idx, size_t qarg_idx, QkInstructionProperties *inst_props)`

Retrieve the qargs for the operation stored in its respective indices.

Panics if any of the indices are out of range.

#### Example

```c
QkTarget *target = qk_target_new(5);

QkTargetEntry *entry = qk_target_entry_new(QkGate_CX);
uint32_t qargs[2] = {0, 1};
qk_target_entry_add_property(entry, qargs, 2, 0.0, 0.1);
qk_target_add_instruction(target, entry);

QkInstructionProperties inst_props;
qk_target_op_props(target, 0, 0, &inst_props);
```

#### Safety

Behavior is undefined if `target` is not a valid, non-null pointer to a `QkTarget`. Behavior is undefined if `inst_props` does not point to an address of the correct size to store `QkInstructionProperties` in.

**Parameters**

- **target** – A pointer to the `QkTarget`.
- **op\_idx** – The index in which the gate is stored.
- **qarg\_idx** – The index in which the qargs are stored.
- **inst\_props** – A pointer to write out the `QkInstructionProperties` instance.

### qk\_target\_op\_get

`void qk_target_op_get(const QkTarget *target, size_t index, QkTargetOp *out_op)`

Retrieves information about an operation in the Target via index. If the index is not present, this function will panic. You can check the `QkTarget` total number of instructions using `qk_target_num_instructions`.

#### Example

```c
QkTarget *target = qk_target_new(5);

QkTargetEntry *entry = qk_target_entry_new(QkGate_CX);
uint32_t qargs[2] = {0, 1};
qk_target_entry_add_property(entry, qargs, 2, 0.0, 0.1);
qk_target_add_instruction(target, entry);

QkTargetOp op;
qk_target_op_get(target, 0, &op);

// Clean up after you're done
qk_target_op_clear(&op);
```

#### Safety

Behavior is undefined if `target` is not a valid, non-null pointer to a `QkTarget`. Behavior is undefined if `out_op` does not point to an address of the correct size to store `QkTargetOp` in.

**Parameters**

- **target** – A pointer to the `QkTarget`.
- **index** – The index in which the gate is stored.
- **out\_op** – A pointer to the space where the `QkTargetOp` will be stored.

### qk\_target\_op\_gate

`QkGate qk_target_op_gate(const QkTarget *target, size_t index)`

Tries to retrieve a `QkGate` based on the operation stored in an index. The user is responsible for checking whether this operation is a gate in the `QkTarget` via using `qk_target_op_get`. If not, this function will panic.

#### Example

```c
QkTarget *target = qk_target_new(5);

QkTargetEntry *entry = qk_target_entry_new(QkGate_CX);
uint32_t qargs[2] = {0, 1};
qk_target_entry_add_property(entry, qargs, 2, 0.0, 0.1);
qk_target_add_instruction(target, entry);

QkTargetOp op;
qk_target_op_get(target, 0, &op);

// Check if the operation is a gate;
if (op.op_type == QkOperationKind_Gate) {
    QkGate gate = qk_target_op_gate(target, 0);
    // Do something
}

// Clean up after you're done.
qk_target_op_clear(&op);
```

#### Safety

Behavior is undefined if the `target` pointer is null or not aligned.

**Parameters**

- **target** – A pointer to the `Target` instance.
- **index** – The index at which the operation is located.

**Returns**

The `QkGate` enum in said index.

### qk\_target\_op\_clear

`void qk_target_op_clear(QkTargetOp *op)`

Clears the `QkTargetOp` object.

#### Safety

The behavior will be undefined if the pointer is null or not-aligned. The data belonging to a `QkTargetOp` originates in Rust and can only be freed using this function.

**Parameters**

- **op** – The pointer to a `QkTargetOp` object.
