es.davy.ai

Preguntas y respuestas de programación confiables

¿Tienes una pregunta?

Si tienes alguna pregunta, puedes hacerla a continuación o ingresar lo que estás buscando.

Sobrecarga del operador variádico [] en C++

Estoy buscando usar las expresiones pasadas en el operador []. Pensé que usando argumentos de plantilla variádicos funcionaría, pero me equivoqué… ¿Hay alguna forma de hacer esto en c++11?

class object {

private:

public:
  void values() { std::cout << "finalizado" << std::endl; }
  template <typename t,="" typename...="" type=""> void values(T arg, Type... args) {

std::cout << arg << "  " << std::endl;
values(args...);
}

template<typename... type=""> void operator[](Type... args) {

   values(args...);
}
};

int main(void) {
  object o1 = object();

o1.values(1, 6.2, true, "hola"); // Funciona bien.

o1[1, 6.2, true]; // Solo se imprime el último valor, por ejemplo, true

return 0;
}

El objetivo más amplio es que me pidieron que hiciera una sintaxis de trabajo para esto
```cpp
let o3 = object [ values 1, "2", true, -3.14 ];
let o1 = object [ key("x") = -1, key("y") = -2,values 1, "2", true, -3.14 ]; // no faltan comas

en c++11 usando c++11 STL (plantillas, using, MACROS, sobrecarga de operadores, etc.). Estoy tratando de descubrir cómo reunir esto lentamente.</typename…>

Tags:  , , ,

Answer

  1. Avatar for davy.ai

    Desafortunadamente, el uso de argumentos de plantilla variádicos por sí solos no permitirá acceder a las expresiones pasadas en el operador []. Sin embargo, hay formas alternativas de lograr esto en C++11. Un enfoque podría ser utilizar una clase anidada para almacenar los valores y operadores que se pasan, y luego acceder a ellos utilizando funciones o sobrecarga de operadores.

    Aquí hay un ejemplo de implementación de cómo esto podría funcionar:

    #include <iostream>
    
    class objeto {
    private:
        class Anidado {
        public:
            template<typename t="">
            Anidado& operator=(T&& t) {
                valores.push_back(std::forward<t>(t));
                return *this;
            }
            std::vector<std::string> claves;
            std::vector<std::string> valores;
        };
    public:
        Anidado operator[](const std::string& clave) {
            Anidado anidado;
            anidado.claves.push_back(clave);
            return anidado;
        }
        void imprimir() {
            for (int i = 0; i < valores_.size(); i++) {
                std::cout << valores_[i] << std::endl;
            }
            std::cout << "Claves: ";
            for (int i = 0; i < claves_.size(); i++) {
                std::cout << claves_[i] << " ";
            }
            std::cout << std::endl;
        }
    private:
        std::vector<std::string> claves_;
        std::vector<std::string> valores_;
    };
    
    int main() {
        objeto o1;
        o1["clave1"] = "valor1";
        o1["clave2"] = "valor2";
        o1.imprimir(); // Salida: valor1 valor2 Claves: clave1 clave2
        return 0;
    }
    

    En este ejemplo, la clase Anidado almacena las claves y valores que se pasan en el operador [], y sobrecarga el operador de asignación para agregarlos a sus propios vectores. Luego, el operator[] de la clase objeto devuelve una instancia de Anidado que se puede utilizar para establecer pares clave-valor. Finalmente, la función imprimir() muestra cómo se almacenan los pares clave-valor en la instancia del objeto.

    Este enfoque se puede extender para permitir el paso de expresiones arbitrarias en el operador [] utilizando plantillas y sobrecarga de operadores. Sin embargo, la implementación se volverá más compleja y requerirá un esfuerzo significativo.

Comments are closed.