---
title: VF2 compiler-pass objects (latest version)
description: API reference for VF2 compiler-pass objects in the latest version of qiskit-c
source: https://quantum.cloud.ibm.com/docs/en/api/qiskit-c/qk-vf-2-layout
---

# VF2 compiler-pass objects

## QkVF2LayoutConfiguration

```c
typedef struct QkVF2LayoutConfiguration QkVF2LayoutConfiguration
```

The configuration for the VF2 layout passes. This is an encapsulated configuration to allow for changes in the API over time; you create and mutate this using the constructor and setters below.

### qk\_vf2\_layout\_configuration\_new

`QkVF2LayoutConfiguration *qk_vf2_layout_configuration_new(void)`

Create a new configuration for the VF2 passes that runs everything completely unbounded.

Call `qk_vf2_layout_configuration_free` with the return value to free the memory when done.

**Returns**

A pointer to the configuration.

### qk\_vf2\_layout\_configuration\_free

`void qk_vf2_layout_configuration_free(QkVF2LayoutConfiguration *config)`

Free a `QkVf2LayoutConfiguration` object.

#### Safety

Behavior is undefined if `config` is a non-null pointer, but does not point to a valid, aligned `QkVF2LayoutConfiguration` object.

**Parameters**

- **config** – A pointer to the configuration.

### qk\_vf2\_layout\_configuration\_set\_call\_limit

`void qk_vf2_layout_configuration_set_call_limit(QkVF2LayoutConfiguration *config, int64_t before, int64_t after)`

Limit the numbers of times that the VF2 algorithm will attempt to extend its mapping before and after it finds the first match.

The VF2 algorithm keeps track of the number of steps it has taken, and terminates when it reaches the limit. After the first match is found, the limit swaps from the “before” limit to the “after” limit without resetting the number of steps taken.

#### Safety

Behavior is undefined if `config` is not a valid, aligned, non-null pointer to a `QkVF2LayoutConfiguration`.

**Parameters**

- **config** – The configuration to update.
- **before** – The number of attempts to allow before the first match is found. Set to a negative number to have no bound.
- **after** – The number of attempts to allow after the first match (if any) is found. Set to a negative number to have no bound.

### qk\_vf2\_layout\_configuration\_set\_time\_limit

`void qk_vf2_layout_configuration_set_time_limit(QkVF2LayoutConfiguration *config, double limit)`

Limit the runtime of the VF2 search.

This is not a hard limit; it is only checked when an improved layout is encountered. Using this option also makes the pass non-deterministic. It is generally recommended to use `qk_vf2_layout_configuration_set_call_limit` instead.

#### Safety

Behavior is undefined if `config` is not a valid, aligned, non-null pointer to a `QkVF2LayoutConfiguration`.

**Parameters**

- **config** – The configuration to update.
- **limit** – The time in seconds to allow. Set to a non-positive value to run with no limit.

### qk\_vf2\_layout\_configuration\_set\_max\_trials

`void qk_vf2_layout_configuration_set_max_trials(QkVF2LayoutConfiguration *config, uint64_t limit)`

Limit the total number of complete improvements found.

Since the VF2 search tree is pruned on-the-fly based on scoring in the `QkTarget`, this limit is not especially powerful. See `qk_vf2_layout_configuration_set_call_limit` for a tighter bound.

#### Safety

Behavior is undefined if `config` is not a valid, aligned, non-null pointer to a `QkVF2LayoutConfiguration`.

**Parameters**

- **config** – The configuration to update.
- **limit** – The number of complete layouts to allow before terminating. Set to 0 to run unbounded.

### qk\_vf2\_layout\_configuration\_set\_shuffle\_seed

`void qk_vf2_layout_configuration_set_shuffle_seed(QkVF2LayoutConfiguration *config, uint64_t seed)`

Activate node shuffling of the input graphs with a given seed.

This effectively drives a modification of the matching order of VF2, which in theory means that the space of a bounded search is not biased based on the node indices. In practice, Qiskit uses the VF2++ ordering improvements when running in “average” mode (corresponding to initial layout search), and starts from the identity mapping in “exact” made. Both of these ordering heuristics are typically far more likely to find results for the given problem than randomization.

If this function was not called, no node shuffling takes place.

#### Safety

Behavior is undefined if `config` is not a valid, aligned, non-null pointer to a `QkVF2LayoutConfiguration`.

**Parameters**

- **config** – The configuration to update.
- **seed** – The seed to use for the activated shuffling.

### qk\_vf2\_layout\_configuration\_set\_score\_initial

`void qk_vf2_layout_configuration_set_score_initial(QkVF2LayoutConfiguration *config, bool score_initial)`

Whether to eagerly score the initial “trivial” layout of the interaction graph.

You typically want to set this `true` if you are using the VF2 passes to improve a circuit that is already lowered to hardware, in order to set a baseline for the score-based pruning. If not, you can leave this as `false` (the default), to avoid a calculation that likely will not have any impact.

#### Safety

Behavior is undefined if `config` is not a valid, aligned, non-null pointer to a `VF2LayoutConfiguration`.

**Parameters**

- **config** – The configuration to update.
- **score\_initial** – Whether to eagerly score the initial trivial layout.

## QkVF2LayoutResult

```c
typedef struct QkVF2LayoutResult QkVF2LayoutResult
```

When running the `qk_transpiler_pass_standalone_vf2_layout` function it returns its analysis result as a `QkVF2LayoutResult` object. This object contains the outcome of the transpiler pass, whether the pass was able to find a layout or not, and what the layout selected by the pass was.

### Functions

#### qk\_vf2\_layout\_result\_has\_match

`bool qk_vf2_layout_result_has_match(const QkVF2LayoutResult *layout)`

Check whether a result was found.

A `true` value includes the situation where the configuration specified to try the “trivial” layout and it was found to be the best (and consequently no qubit relabelling is necessary, other than ancilla expansion if appropriate). See `qk_vf2_layout_result_has_improvement` to distinguish whether an explicit remapping is stored.

##### Safety

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

**Parameters**

- **layout** – a pointer to the layout

**Returns**

`true` if the VF2-based layout pass found any match.

#### qk\_vf2\_layout\_result\_has\_improvement

`bool qk_vf2_layout_result_has_improvement(const QkVF2LayoutResult *layout)`

Check whether the result is an improvement to the trivial layout.

##### Safety

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

**Parameters**

- **layout** – a pointer to the layout

**Returns**

`true` if the VF2-based layout pass found an improved match.

#### qk\_vf2\_layout\_result\_map\_virtual\_qubit

`uint32_t qk_vf2_layout_result_map_virtual_qubit(const QkVF2LayoutResult *layout, uint32_t qubit)`

Get the physical qubit for a given virtual qubit

##### Safety

Behavior is undefined if `layout` is not a valid, non-null pointer to a `QkVF2LayoutResult` containing a result, or if the qubit is out of range for the initial circuit.

**Parameters**

- **layout** – a pointer to the layout
- **qubit** – the virtual qubit to get the physical qubit of

**Returns**

The physical qubit mapped to by the specified virtual qubit

#### qk\_vf2\_layout\_result\_free

`void qk_vf2_layout_result_free(QkVF2LayoutResult *layout)`

Free a `QkVF2LayoutResult` object

##### Example

```c
QkCircuit *qc = qk_circuit_new(1, 0);
```

##### Safety

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

**Parameters**

- **layout** – a pointer to the layout to free
