code review c++ – Empaque y desempaque de brocas

Pregunta:

Necesitaba una función variable para empaquetar y desempaquetar bits en tipos enteros. Este es mi primer intento:

template<typename T>
constexpr T pack(bool b)
{
    return b;
}

template<typename T, typename... Types>
constexpr T pack(bool b, Types... args)
{
    return (b << sizeof...(Types)) | pack<T>(args...);
}

template<typename T, typename... Types>
void unpack(T packed, bool& b1)
{
    b1 = packed & 1;
}

template<typename T, typename... Types>
void unpack(T packed, bool& b1, Types&... args)
{
    b1 = packed & (1 << sizeof...(Types));
    unpack(packed, args...);
}

Ejemplo de uso:

int main(void)
{
    std::cout << pack<int>(1, 0, 0, 1, 0, 1, 1, 0) << std::endl; // 150
    std::cout << pack<int>(1, 0, 1) << std::endl; // 5
    int val = pack<int>(1, 0, 1);
    bool b1, b2, b3;
    unpack(val, b1, b2, b3);
    std::cout << b1 << " " << b2 << " " << b3 << std::endl; // 1 0 1
}

¿Este código contiene algún error, se puede mejorar y las plantillas variadas se usan correctamente aquí (todavía no domino su sintaxis)?

Respuesta:

Falta verificación de desbordamiento

Una falla grave que veo en este código es que el usuario necesita determinar la cantidad de parámetros para unpack . Esto no es válido para una función cuya salida depende de una entrada de tiempo de ejecución. Peor aún, no hay verificación que le diga al usuario que el número real supera la cantidad de bits dados para desempaquetar.

Una posible solución sería devolver un std::vector<bool> para ajustar el número entero.

La otra solución sería conservar la interfaz actual pero introducir una notificación de error (por excepción o código de retorno).

Parámetro de plantilla innecesario

Otra cosa con respecto a la función de unpack : parece que no necesita el parámetro Types al final de la recursión, por lo que se convierte en:

template<typename T>
void unpack(T packed, bool& b1)
{
    b1 = packed & 1;
}

Denominación

Los nombres de los parámetros de función podrían ser mejores. Supongo que b1 solo es apropiado en la llamada de nivel superior de la función. No puedo decidirme por un nombre mejor ahora, pero debería indicar que es el bit actual. Del mismo modo, los args deben llamarse remainingBits o algo como esto.

Leave a Comment

Your email address will not be published. Required fields are marked *

web tasarım