Finish basic buffer implementation.
This commit is contained in:
parent
1bc5bc0b10
commit
f8041c2bfa
72
Buffer.cc
72
Buffer.cc
|
@ -29,7 +29,7 @@ nearestPower(size_t x)
|
|||
x |= x >> 16;
|
||||
x |= x >> 32;
|
||||
|
||||
return x;
|
||||
return x+1;
|
||||
}
|
||||
|
||||
|
||||
|
@ -56,6 +56,14 @@ Buffer::Buffer(const char *data)
|
|||
}
|
||||
|
||||
|
||||
bool
|
||||
Buffer::Append(const char *s)
|
||||
{
|
||||
size_t slen = strnlen(s, maxReasonableLine);
|
||||
|
||||
return this->Append((uint8_t *)s, slen);
|
||||
}
|
||||
|
||||
bool
|
||||
Buffer::Append(uint8_t *data, size_t datalen)
|
||||
{
|
||||
|
@ -78,12 +86,23 @@ Buffer::Append(uint8_t c)
|
|||
return this->Append(&c, 1);
|
||||
}
|
||||
|
||||
|
||||
bool
|
||||
Buffer::Insert(size_t index, const char *s)
|
||||
{
|
||||
size_t slen = strnlen(s, maxReasonableLine);
|
||||
|
||||
return this->Insert(index, (uint8_t *)(s), slen);
|
||||
}
|
||||
|
||||
|
||||
bool
|
||||
Buffer::Insert(size_t index, uint8_t *data, size_t datalen)
|
||||
{
|
||||
auto resized = this->shift(index, datalen);
|
||||
auto resized = this->shiftRight(index, datalen);
|
||||
|
||||
memcpy(this->contents + index, data, datalen);
|
||||
this->length += datalen;
|
||||
return resized;
|
||||
}
|
||||
|
||||
|
@ -94,6 +113,23 @@ Buffer::Insert(size_t index, uint8_t c)
|
|||
}
|
||||
|
||||
|
||||
bool
|
||||
Buffer::Remove(size_t index, size_t count)
|
||||
{
|
||||
auto resized = this->shiftLeft(index, count);
|
||||
|
||||
this->length -= count;
|
||||
return resized;
|
||||
}
|
||||
|
||||
|
||||
bool
|
||||
Buffer::Remove(size_t index)
|
||||
{
|
||||
return this->Remove(index, 1);
|
||||
}
|
||||
|
||||
|
||||
void
|
||||
Buffer::Resize(size_t newCapacity)
|
||||
{
|
||||
|
@ -103,6 +139,7 @@ Buffer::Resize(size_t newCapacity)
|
|||
|
||||
uint8_t *newContents = new uint8_t[newCapacity];
|
||||
|
||||
memset(newContents, 0, newCapacity);
|
||||
if (this->length > 0) {
|
||||
memcpy(newContents, this->contents, this->length);
|
||||
}
|
||||
|
@ -140,8 +177,9 @@ Buffer::Clear()
|
|||
void
|
||||
Buffer::Reclaim()
|
||||
{
|
||||
this->Clear();
|
||||
|
||||
delete this->contents;
|
||||
this->length = 0;
|
||||
this->capacity = 0;
|
||||
}
|
||||
|
||||
|
@ -158,7 +196,7 @@ Buffer::mustGrow(size_t delta)
|
|||
|
||||
|
||||
bool
|
||||
Buffer::shift(size_t offset, size_t delta)
|
||||
Buffer::shiftRight(size_t offset, size_t delta)
|
||||
{
|
||||
auto resized = false;
|
||||
auto newCap = this->mustGrow(delta);
|
||||
|
@ -168,13 +206,31 @@ Buffer::shift(size_t offset, size_t delta)
|
|||
resized = true;
|
||||
}
|
||||
|
||||
|
||||
for (size_t i = this->length; i >= offset; i++) {
|
||||
this->contents[i+delta] = this->contents[i];
|
||||
}
|
||||
if (this->length == 0) return 0;
|
||||
|
||||
memmove(this->contents+(offset+delta), this->contents+offset, this->length);
|
||||
return resized;
|
||||
}
|
||||
|
||||
|
||||
bool
|
||||
Buffer::shiftLeft(size_t offset, size_t delta)
|
||||
{
|
||||
auto resized = false;
|
||||
|
||||
for (size_t i = offset; i < this->length; i++) {
|
||||
this->contents[i] = this->contents[i+delta];
|
||||
}
|
||||
|
||||
return this->Trim() != 0;
|
||||
}
|
||||
|
||||
|
||||
uint8_t&
|
||||
Buffer::operator[](size_t index)
|
||||
{
|
||||
return this->contents[index];
|
||||
}
|
||||
|
||||
|
||||
} // namespace klib
|
||||
|
|
21
Buffer.h
21
Buffer.h
|
@ -14,19 +14,24 @@ namespace klib {
|
|||
class Buffer {
|
||||
public:
|
||||
Buffer();
|
||||
Buffer(size_t);
|
||||
Buffer(const char *);
|
||||
explicit Buffer(size_t);
|
||||
explicit Buffer(const char *);
|
||||
~Buffer() { this->Reclaim(); }
|
||||
|
||||
uint8_t *Contents() { return this->contents; }
|
||||
size_t Size() { return this->length; };
|
||||
size_t Capacity() { return this->capacity; }
|
||||
size_t Length() const { return this->length; };
|
||||
size_t Capacity() const { return this->capacity; }
|
||||
|
||||
bool Append(const char *s);
|
||||
bool Append(uint8_t *data, size_t datalen);
|
||||
bool Append(uint8_t c);
|
||||
|
||||
bool Insert(size_t index, const char *s);
|
||||
bool Insert(size_t index, uint8_t *data, size_t datalen);
|
||||
bool Insert(size_t index, uint8_t c);
|
||||
|
||||
// bool Remove(size_t index, size_t length);
|
||||
bool Remove(size_t index, size_t count);
|
||||
bool Remove(size_t index); // remove single char
|
||||
|
||||
/* memory management */
|
||||
void Resize(size_t newCapacity);
|
||||
|
@ -34,15 +39,19 @@ public:
|
|||
void Clear();
|
||||
void Reclaim();
|
||||
|
||||
uint8_t &operator[](size_t index);
|
||||
private:
|
||||
size_t mustGrow(size_t delta);
|
||||
bool shift(size_t offset, size_t delta);
|
||||
bool shiftRight(size_t offset, size_t delta);
|
||||
bool shiftLeft(size_t offset, size_t delta);
|
||||
|
||||
uint8_t *contents;
|
||||
size_t length;
|
||||
size_t capacity;
|
||||
};
|
||||
|
||||
|
||||
|
||||
} // namespace klib
|
||||
|
||||
#endif //KGE_BUFFER_H
|
||||
|
|
|
@ -11,6 +11,19 @@ main()
|
|||
std::cout << buffer.Contents() << std::endl;
|
||||
|
||||
buffer.Insert(1, (uint8_t *)"el", 2);
|
||||
buffer.Append('!');
|
||||
|
||||
std::cout << buffer.Contents() << std::endl;
|
||||
|
||||
buffer.Remove(buffer.Length()-1);
|
||||
buffer.Remove(0, 5);
|
||||
buffer.Insert(0, 'g');
|
||||
buffer.Insert(1, (uint8_t *)"oodbye", 6);
|
||||
|
||||
buffer.Reclaim();
|
||||
buffer.Append("and now for something completely different...");
|
||||
|
||||
std::cout << buffer.Contents() << std::endl;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue