Per il compilatore il tipo enum luce è una variabile che può assumere i valori 0,1 o 2.
Rispettivamente intercambiabili con Rosso,Verde e Giallo.
Questo è ciò che è valido per il compilatore, trattala come se fosse una variabile qualsiasi, con la differenza che ha come dominio {0,1,2}.
Non esiste che il programma capisce in maniera automatica come stampare una variabile di tipo luce.Non sa come stamparla, non è un umano e non sa che se ha valore 0 (oppure valore Rosso), deve stampare la stringa "Rosso", Rosso a compile-time è soltanto un' etichetta che identifica il valore zero per enum luce.
Quindi puoi definire tu un operatore:

codice:
ostream& operator<< (ostream& os, const luce& l)
{
    switch(l)
    {
        case Rosso:
            os << "Rosso";
            break;
        case Verde:
            os << "Verde";
            break;
        case Giallo:
           os << "Giallo";
    }
    return os;
}