Source code for spikify.encoding.temporal.global_referenced.phase_encoding_algorithm
""".. raw:: html <h2>Phase Encoding Algorithm</h2>"""importnumpyasnp
[docs]defphase_encoding(signal:np.ndarray,num_bits:int)->np.ndarray:""" Perform phase encoding on the input signal based on the given settings. This function encodes the input signal by calculating the phase angles of the normalized signal and quantizing these angles into a binary spike train representation. The encoding process uses a specified number of bits to determine the level of quantization. Refer to the :ref:`phase_encoding_algorithm_desc` for a detailed explanation of the Phase Encoding Algorithm. **Code Example:** .. code-block:: python import numpy as np from spikify.encoding.temporal.global_referenced import phase_encoding signal = np.array([0.1, 0.2, 0.3, 1.0, 0.5, 0.3, 0.1, 0.2]) num_bits = 4 encoded_signal = phase_encoding(signal, num_bits) .. doctest:: :hide: >>> import numpy as np >>> from spikify.encoding.temporal.global_referenced import phase_encoding >>> signal = np.array([0.1, 0.2, 0.3, 1.0, 0.5, 0.3, 0.1, 0.2]) >>> num_bits = 4 >>> encoded_signal = phase_encoding(signal, num_bits) >>> encoded_signal array([1, 1, 1, 1, 1, 0, 0, 0], dtype=uint8) :param signal: The input signal to be encoded. This should be a numpy ndarray. :type signal: numpy.ndarray :param num_bits: The number of bits to use for encoding. :type num_bits: int :return: A 1D numpy array representing the phase-encoded spike train. :rtype: numpy.ndarray :raises ValueError: If the input signal is empty or if the number of bits is not appropriate for the signal length. """# Check for invalid inputsiflen(signal)==0:raiseValueError("Signal cannot be empty.")iflen(signal)%num_bits!=0:raiseValueError(f"The phase_encoding num_bits ({num_bits}) is not a multiple of the signal length ({len(signal)}).")# Ensure non-negative signal valuessignal=np.clip(signal,0,None)# Compute mean over the signal reshaped to bit-sized chunkssignal=np.mean(signal.reshape(-1,num_bits),axis=1)# Normalize the signal if the maximum is greater than 0signal_max=signal.max()ifsignal_max>0:signal/=signal_max# Compute the phase angles based on the signalphase=np.arcsin(signal)# Create phase bins and quantize the phasebins=np.linspace(0,np.pi/2,2**num_bits+1)levels=np.searchsorted(bins,phase)# Adjust levels to avoid out-of-range valueslevels=np.clip(levels,0,2**num_bits-1)# Convert levels to binary and flatten the result to a 1D spike arrayspikes=np.array([list(map(int,list(f"{level:0{num_bits}b}")))forlevelinlevels],dtype=np.uint8).reshape(-1)returnspikes