---
title: "Poltergeist (programación informática)"
type: "antipattern"
slug: "poltergeist"
url: "http://localhost:3000/es/antipatterns/poltergeist.md"
description: "Objeto efímero inapropiado"
---
# Poltergeist (programación informática)

> Objeto efímero inapropiado

En la [programación informática](https://en.wikipedia.org/wiki/Computer%5Fprogramming "Computer programming"), un **poltergeist** (o **carromato gitano**) es un objeto efímero, normalmente [sin estado](https://en.wikipedia.org/wiki/State%5F%28computer%5Fscience%29 "State (computer science)"), que se utiliza para realizar la inicialización o para invocar métodos en otra clase más permanente. Se considera un [antipatrón](https://en.wikipedia.org/wiki/Anti-pattern "Anti-pattern"). La definición original es de Michael Akroyd en la conferencia Object World West de 1996:

> Igual que un [carromato gitano](https://en.wikipedia.org/wiki/Vardo%5F%28Romani%5Fwagon%29 "Vardo (Romani wagon)") o un [poltergeist](https://en.wikipedia.org/wiki/Poltergeist "Poltergeist") aparece y desaparece de forma misteriosa, así lo hace este objeto de corta vida. Como consecuencia, el código es más difícil de mantener y se produce un desperdicio innecesario de recursos. La causa típica de este antipatrón es un diseño deficiente de objetos.

A menudo, un poltergeist puede identificarse por su nombre; estos suelen incluir en el nombre palabras como "Manager", "Controller", "Supervisor", "StartProcess", etc.

A veces, las clases poltergeist se crean porque el [programador](https://en.wikipedia.org/wiki/Programmer "Programmer") anticipó la necesidad de una arquitectura más compleja. Por ejemplo, surge un poltergeist si el mismo método actúa a la vez como _cliente_ e _invocador_ en un [patrón Command](https://en.wikipedia.org/wiki/Command%5Fpattern "Command pattern"), y el programador anticipa la separación de ambas fases. Sin embargo, esta arquitectura más compleja puede que en realidad nunca llegue a materializarse.

Los poltergeists no deben confundirse con los objetos longevos y portadores de estado de un [patrón](https://en.wikipedia.org/wiki/Software%5Fdesign%5Fpattern "Software design pattern") como el [modelo–vista–controlador](https://en.wikipedia.org/wiki/Model%E2%80%93view%E2%80%93controller "Model–view–controller"), ni con los patrones de separación en capas como el [patrón business delegate](https://en.wikipedia.org/wiki/Business%5Fdelegate%5Fpattern "Business delegate pattern").

Para eliminar un poltergeist, borra la clase e inserta su funcionalidad en la clase invocada, posiblemente mediante [herencia](https://en.wikipedia.org/wiki/Inheritance%5F%28object-oriented%5Fprogramming%29 "Inheritance (object-oriented programming)") o como un [mixin](https://en.wikipedia.org/wiki/Mixin "Mixin").

Se han propuesto métodos para detectar poltergeists en el código con vistas a la refactorización.

## Ejemplo

La clase `Poltergeist` de este ejemplo en [C++](https://en.wikipedia.org/wiki/C%2B%2B "C++") puede considerarse un "objeto poltergeist", ya que no añade funcionalidad ni encapsulación adicionales y solo aumenta la complejidad con una abstracción innecesaria.

import std;

using String = std::string;

// Clase Poltergeist que solo guarda un puntero, pero no añade ningún comportamiento útil
class Poltergeist {
private:
    String* s; // puntero a string, pero la clase en sí no hace nada útil
public:
    explicit Poltergeist(String* s):
        s{s} {}

    ~Poltergeist() {
        delete s;
    }

    [[nodiscard]]
    String get() const noexcept {
        return s;
    }

    // Sin comportamiento adicional ni funcionalidad útil
};

int main() {
    // Crear un objeto Poltergeist que solo guarda un puntero a la cadena
    Poltergeist p(new String("Hello, world!"));

    // Solo pasa los datos de un lado a otro sin aportar valor
    std::println(*p.get());

    return 0;
}

En su lugar, esto podría hacerse de forma más apropiada usando un [puntero inteligente](https://en.wikipedia.org/wiki/Smart%5Fpointer "Smart pointer").

import std;

using String = std::string;
template <typename T>
using UniquePtr = std::unique_ptr<T>;

// Usar punteros inteligentes directamente para gestionar la memoria
UniquePtr<String> s = std::make_unique<String>("Hello, World!");
std::println(*s);

Otro ejemplo de objeto poltergeist/carromato gitano es el siguiente, donde `UserCreator` se instancia solo para realizar algunas acciones básicas.

import std;

using String = std::string;

class UserManager {
public:
    void createUser(const String& name) {
        std::println("User created: {}", name);
    }
};

// La clase poltergeist
class UserCreator {
public:
    explicit UserCreator(const String& name) {
        UserManager manager;
        manager.createUser(name);
    }
};

int main() {
    // Crear un poltergeist solo para llamar a createUser()
    UserCreator("Alice");
    UserCreator("Bob");
}

Esto podría hacerse de forma más apropiada de la siguiente manera, evitando por completo cualquier clase poltergeist:

// Evitar por completo el poltergeist UserCreator
int main() {
    UserManager manager;
    manager.createUser("Alice");
    manager.createUser("Bob");
}
