Newsgroup: it.comp.lang.c++
Titolo: stream a /dev/null

ho una funzione che ritorna uno stream,
che viene usato per loggare
in certi casi voglio che l'output venga ignorato
come faccio (senza creare un altro stream)
non c'e' uno standard stream "null" ?
help
ciao
Simone

 non c'e' uno standard stream "null" ?
no, ma puoi aprire /dev/null e scriverci sopra:
FILE *null;
null = fopen("/dev/null","w");
fprintf(null,"log inutile");
ciao
Kronos
-- 
Home: 
http://kronoz.cjb.net
Il piu` bel momento dell'amore e` quando ci si illude che duri
per sempre; il piu` brutto, quando ci si accorge che dura
da troppo.

 ha scritto nel messaggio
news:20010413.121349...@pengo.reitek.com...

Nello Standard non è previsto, ma la libreria di I/O è pensata per
essere
estesa quindi....
Ecco un esempio (probabilmente non è di immediata comprensione ma
basta
leggersi un buon manuale che tratti gli iostream).
#ifndef nullstream_hpp_
#define nullstream_hpp_
#include <streambuf>
#include <ostream>
namespace std
{
  class nullbuf: public streambuf
  {
    public:
       // types
       typedef char                    char_type;
       typedef char_traits<char_type>  traits_type;
       typedef traits_type::int_type   int_type;
       typedef traits_type::off_type   off_type;
       typedef traits_type::pos_type   pos_type;
    private:
       static const size_t SIZE = 512;
       // per efficienza è comunque bufferizzato
       char_type buf[SIZE];
       size_t bytes_written;
    public:
       nullbuf()
       : bytes_written(0)
       {
          setp(buf, buf + SIZE);
       }
       // numero di caratteri inviati
       size_t pcount() const
       {
          return bytes_written + (pptr() - pbase());
       }
    protected:
       int_type overflow(int_type c = traits_type::eof())
       {
          // semplicemente riutilizza il buffer ciclicamente
          setp(buf, buf + SIZE);
          bytes_written += SIZE;
          return traits_type::not_eof(c);
       }
       int sync() { return 0; }
       // per efficienza;
       // è usato da write e operator<<(const char*)
       streamsize xsputn(const char_type*, streamsize n)
       {
          bytes_written += n;
          return n;
       }
  };
  class nullstream: public ostream
  {
    public:
       // types
       typedef char                    char_type;
       typedef char_traits<char_type>  traits_type;
       typedef traits_type::int_type   int_type;
       typedef traits_type::off_type   off_type;
       typedef traits_type::pos_type   pos_type;
    private:
       nullbuf buf;
    public:
       nullstream()
       : ostream(0), buf()
       {
          init(&buf);
       }
       nullbuf* rdbuf() const { return const_cast<nullbuf*>(&buf); }
       size_t pcount() const { return buf.pcount(); }
  };
}
#endif
Saluti   Manlio Perillo

 fprintf(null,"log inutile");
Solo se lavora su Unix o derivati. Altrimenti potrebbe scriversi uno
stream buffer che si limita ad ingoiare i caratteri. Se e' ancora in
giro Manlio Perillo e' certamente piu' in grado di me di dare
indicazioni.
Ciao,
Nicola

 indicazioni.
...come ovviamente aveva gia' fatto in un altro messaggio.
Ciao,
Nicola

 ha scritto nel messaggio
news:3ADD709A...@divalsim.it...

Effettivamente la libreria di I/O è una delle cose che più mi
affascina del C++.
A mio avviso sfrutta appieno l'approccio OOP
(distinsione fra scrittura dei singoli caratteri *raw* su un device
 - streambuf -, formattazione dei tipi - locale - e gestione del
tutto - iostream -).
Questo permette di agire singolarmente su di un singolo aspetto,
sfruttando poi il framework per il resto.
Ciao  Manlio Perillo

 affascina del C++.
Sarai invidioso di sapere allora che un paio di settimane fa ho
assistito ad una presentazione di Angelika Langer, co-autrice di
"Standard C++ IOStreams & Locales", competente e brava a spiegare.
Ciao,
Nicola

 sfruttando poi il framework per il resto.
Si. E' la parte piu' OO della libreria standard. Non commento i locale (che e'
una parthe dello standard che praticamente non conosco per nulla) ma sulla
gestione di streambuf avrei da dire qualche cosa: si potrebbero separare
ulteriormente i "concern". Ovvero separare l'interfaccia di I/O (il lato visto
da iostream) dal concetto di buffering e poi questo dal concetto di I/O fisico.
--
Andrea Ferro
---------
Brainbench C++ Master. Scored higher than 97% of previous takers
Scores: Overall 4.46, Conceptual 5.0, Problem-Solving 5.0
More info 
http://www.brainbench.com/transcript.jsp?pid=2522556

 wrote in message
news:3ADD7E6A...@divalsim.it...

Se la presentazione era "privata", ovvero se la Langer era stata invitata come
consulente della tua azienda ... ti invidio l'azienda!!
Se la presentazione era "pubblica" ti invidio le fonti di informazione dato che
non ne sapevo nulla!
In entrambe i casi invidio la conoscenza della parte relativa ai locale che non
ho mai avuto il tempo di studiarmi (praticamente tutto cio' che so e' che
esistono!).


 esistono!).
Devo dire che sono uscito dalla presentazione della Langer, per altro
piuttosto chiara, con una convinzione: i locale, se li conosci, li
eviti...
Ciao,
Nicola

 eviti...
E' anche la mia sensazione. Persino l'idea di riscriversi una implementazione di
streambuf non e' cosa da fare in tre minuti per un programmatore medio! Ma se e'
per questo anche scrivere codice che gestisce correttamente file di testo in
varie codifiche non e' banalissimo (magari bastasse solo trasformare i char in
wchar_t)!


 ha scritto nel messaggio
news:3ADD7E6A...@divalsim.it...

Molto invidioso...... :)
Di che cosa trattava la presentazione?
Dove si è tenuta?
Ciao
Manlio Perillo


Questo č vero.
Ma usata ad un livello base il framework del locale permette di
fare cose interessanti.
Tipo usare i facet adibiti alla formattazione per convertire
un tipo di dato in stringa e viceversa.
Ecco un esempio:
#include <locale>
#include <iterator>
#include <string>
// scrive (appende) alla fine della stringa
class NumPut_inserter:
      public std::num_put< char,
std::back_insert_iterator<std::string> >
{
   public:
      typedef char char_type;
      typedef std::back_insert_iterator<std::string> iter_type;
      NumPut_inserter()
      : std::num_put<char, iter_type>(1)
      {  }
};
int main()
{
   std::string value;
   float x = 19.1234;
   NumPut_inserter parser;
   parser.put(std::back_inserter(value), std::cout, ' ', x);
   std::cout << "value = " << value << '\n';
}
Saluti   Manlio Perillo

 Ecco un esempio:
Scusa ma il tuo esempio non viene compilato dal mio Borland C++ 5.5.1.
Sbaglio qualcosa io?
EMG

 > Questo č vero.

No, č un problema del Borland C++ 5.5.1.
Prova a definire la macro:
#define _RWSTD_COMPILE_INSTANTIATE  1
Manlio Perillo

 #define _RWSTD_COMPILE_INSTANTIATE  1
Ora va. Ma che significa?
EMG

 Ora va. Ma che significa?
in pratica l'hanno messo per costringere il BCC a compilare le librerie 
STD della roguewave. c'era una storia a riguardo, ma non mi rikordo 
dove...


Alcune parti della libreria standard sono precompilate, per accelerare
le compilazioni. Questo pero' rende impossibile aggiungere
specializzazioni o cose simili. La macro sopra definita forza la
ricompilazione.
Ciao,
Nicola

 ricompilazione.
Ho capito. Grazie.
EMG