How can I code a Conditional phase shift transform?

I am interested in implementing a operation in Q#. The operation should follow the algorithm below:

When $$A=0$$ it is quite easy to see that the algorithm states if the qubitt is in nullspace apply a transformation to flip the sign of the qubit.

I am not sure how to use the algorithm for the 'i is in A' case.

The trick here is to define a new operation whose unitary representation is \begin{align} S_a|i\rangle = \begin{cases} -|i\rangle \text{ if } i = a \\ |i\rangle \text{ otherwise } \end{cases}. \end{align}

At that point, $$S_A = \prod_{a \in A} S_a$$. In Q#, you can implement $$S_a$$ easily using the ControlledOnInt operation, an auxillary qubit in the $$|-\rangle$$ state, and an X operation:

operation ApplyConditionalPhase(subset : Int[], register : LittleEndian)
: Unit is Adj + Ctl {
using (aux = Qubit()) {
within {
// prepare aux in the |−⟩ state.
H(aux);
Z(aux);
} apply {
for (element in subset) {
(ControlledOnInt(element, X))(register!, aux);
}
}
}
}


This works using the same phase kickback principle as in the Deutsch−Jozsa algorithm; for more details on how phase kickback works, check out Chapters 6 and 7 of my book.

• What does setting our data type to LittleEndian for our register input do? – Mridul Jun 3 '20 at 3:26
• Also, why do we specify the output is Adj + Ctl? – Mridul Jun 3 '20 at 3:27
• The LittleEndian user-defined type (UDT)_is used to specify that a register of qubits is to be interpreted as encoding an unsigned integer; in this case, that ensures that the user passes in the control register in a format consistent with the ordering expected by ControlledOnInt. For your other question, is Adj + Ctl specifies that the operation is adjointable and controllable, so that you can implement $S_A^{\dagger}$ and controlled applications of $S_A$ automatically. – Chris Granade Jun 3 '20 at 3:30
• last question: what does apply do? can we replace that line by using ApplytoAll or ApplytoEach and containing it into the for loop? – Mridul Jun 3 '20 at 3:30
• Speaking of qsharp.community, we are always looking for posts and content from folks so if you are interested in writing something about what you learned here or anything else you think other community members might find useful, let use know! qsharp.community/blog/call-for-contributions You can see an example of a post we just got today on the Q# + Python install process for Linux: qsharp.community/blog/qsharp-python-linux – Dr. Sarah Kaiser Jun 3 '20 at 4:13
operation ApplyConditionalPhase_0(register: LittleEndian) : Unit is Adj + Ctl
{
using (aux = Qubit())
{
(ControlledOnInt(0,X))(register!,aux);
}
}
operation ApplyConditionalPhase(register : LittleEndian) : Unit is Adj + Ctl
{
using (aux = Qubit())
{
(ControlledOnInt(1,X))(register!,aux);
}
}


I realized this paper treats A as all positive integers, that means not including zero. I am understanding this gate to simply flip the qubit when it is 0 for the first. Since 0 is not in the set of positive integers, we flip all qubits that are 1 to satisfy i = a.