2012-10-24 20 views
16

const char* işaretçisiyle işaret edilen bir arabellekte bazı verilerim var. Veri sadece bir ASCII dizesidir. Onun boyutunu biliyorum. Verilerin akışlardan okunmasıyla aynı şekilde okumak istiyorum.Sabit bellekten bir giriş akışı oluşturma

// for example, data points to a string "42 3.14 blah" 
MemoryStreamWrapper in(data, data_size); 
int x; 
float y; 
std::string w; 
in >> x >> y >> w; 

Önemli durumu: veriler hiçbir şekilde kopyalanamaz veya değiştirilmemelidir (Aksi Ben sadece bir dize akışı kullanmayı tercih ediyorum bana böyle kod yazmak için izin verecek bir çözüm arıyorum En iyi bilgime göre, veri kopyalanmadan bir const char işaretçisinden bir dize akışı oluşturmak mümkün değildir.)

+0

ping @ dietmar-kuhl ... –

+0

'data' türü nedir? Bu const char * 'değil mi? –

+0

Evet, bu '' const char * ' –

cevap

23

Bunu yapmanın yolu, uygun bir akış tamponu oluşturmaktır. Bu, örneğin, bu gibi yapılabilir: kullanılacak önbellekde veri değişmez, ancak arabirimi hala char* gerektirir, esas olarak:

#include <streambuf> 
#include <istream> 

struct membuf: std::streambuf { 
    membuf(char const* base, size_t size) { 
     char* p(const_cast<char*>(base)); 
     this->setg(p, p, p + size); 
    } 
}; 
struct imemstream: virtual membuf, std::istream { 
    imemstream(char const* base, size_t size) 
     : membuf(base, size) 
     , std::istream(static_cast<std::streambuf*>(this)) { 
    } 
}; 

TEK biraz garip bir şey akış tamponunda const_cast<char*>() olan "normal" akış arabelleklerinde arabelleği değiştirmeyi kolaylaştırmak için. Bu ile, normal bir giriş akışı olarak imemstream kullanabilirsiniz:

imemstream in(data, size); 
in >> value; 
+0

Bu 'istringstream''nın pubsetbuf'nın bunu yapmadığını nereden biliyorsunuz? – ildjarn

+0

Sadece normal 'std :: istringstream' ve' .rdbuf() -> pubsetbuf (veri, boyut) 'aracılığıyla aynı şeyi yaratamaz mısınız? – Xeo

+0

Bu, benden daha kolaydı! Sanırım karmaşık olabileceğini düşündüm çünkü soket akışları için aynısını yaptım, bu durumda yüzlerce satır gerektiriyor ... – user1610015

1

Std :: istream alt sınıfının alt sınıfını çizmek için tek yol budur. streambuf) sabit bellekten okuyan kendi akış sınıfınızı oluşturmak için.

C++ standart kitaplık akışı sınıfları oldukça dağınık ve kötü tasarlanmış olduğu için bu kadar kolay değil. Çok fazla ölçeklendirmeye ihtiyacınız olmadıkça buna değmez sanmıyorum.

İlgili konular