Browse Source

Jupiter::String_Type:

* Added more replace() functions
* Added another remove() function
* Added a processEscapeSequences() function
Jupiter::Shift_String_Type:
* Added slight optimization for new remove() function
release/0.19
JustinAJ 10 years ago
parent
commit
f7bd819e5f
  1. 10
      Jupiter/Shift_String.h
  2. 8
      Jupiter/Shift_String_Imp.h
  3. 26
      Jupiter/String_Type.h
  4. 317
      Jupiter/String_Type_Imp.h
  5. BIN
      Release/Jupiter.lib

10
Jupiter/Shift_String.h

@ -60,7 +60,15 @@ namespace Jupiter
* @param value Value of the element to remove. * @param value Value of the element to remove.
* @return True if an element was removed, false otherwise. * @return True if an element was removed, false otherwise.
*/ */
virtual bool remove(const T &value); virtual bool remove(const T &value) override;
/**
* @brief Removes a number of elements starting at an index.
*
* @param index Index to start removing elements at.
* @param length Number of elements to remove.
*/
virtual void remove(size_t index, size_t length) override;
/** /**
* @brief Default constructor for the Shift_String_Type class. * @brief Default constructor for the Shift_String_Type class.

8
Jupiter/Shift_String_Imp.h

@ -64,6 +64,14 @@ template<typename T> bool Jupiter::Shift_String_Type<T>::remove(const T &value)
return Jupiter::String_Type<T>::remove(value); return Jupiter::String_Type<T>::remove(value);
} }
template<typename T> void Jupiter::Shift_String_Type<T>::remove(size_t index, size_t length)
{
if (index == 0)
this->shiftRight(length);
else
Jupiter::String_Type<T>::remove(index, length);
}
template<typename T> bool Jupiter::Shift_String_Type<T>::setBufferSize(size_t len) template<typename T> bool Jupiter::Shift_String_Type<T>::setBufferSize(size_t len)
{ {
if (len > Jupiter::String_Type<T>::length) if (len > Jupiter::String_Type<T>::length)

26
Jupiter/String_Type.h

@ -102,6 +102,20 @@ namespace Jupiter
*/ */
virtual bool remove(const T &value); virtual bool remove(const T &value);
/**
* @brief Removes a number of elements starting at an index.
*
* @param index Index to start removing elements at.
* @param length Number of elements to remove.
*/
virtual void remove(size_t index, size_t length);
/**
* @brief Processes escape sequences in a string.
* Source reference: http://en.cppreference.com/w/cpp/language/escape
*/
virtual void processEscapeSequences();
/** /**
* @brief Sets the value of an element at the specified index. * @brief Sets the value of an element at the specified index.
* Note: If the index is not in the string, it will be added. * Note: If the index is not in the string, it will be added.
@ -137,6 +151,18 @@ namespace Jupiter
virtual size_t insert(size_t index, const T &value); virtual size_t insert(size_t index, const T &value);
virtual size_t insert(size_t index, const Jupiter::Readable_String<T> &value); virtual size_t insert(size_t index, const Jupiter::Readable_String<T> &value);
/**
* @brief Replaces data at an index with a specified value.
*
* @param index Index to start replacing at.
* @param length Number of elements to replace.
* @param value Value to write over the elements.
* @return New size of the string.
*/
virtual size_t replace(size_t index, size_t length, const T &value);
virtual size_t replace(size_t index, size_t length, const T *value, size_t valueSize);
virtual size_t replace(size_t index, size_t length, const Jupiter::Readable_String<T> &value);
/** /**
* @brief Replaces all instances of one value with another value. * @brief Replaces all instances of one value with another value.
* *

317
Jupiter/String_Type_Imp.h

@ -132,14 +132,197 @@ template<typename T> bool Jupiter::String_Type<T>::remove(const T &value)
return false; return false;
} }
template<typename T> void Jupiter::String_Type<T>::remove(size_t index, size_t length)
{
if (index >= Jupiter::String_Type<T>::length)
return;
if (index + length >= Jupiter::String_Type<T>::length)
Jupiter::String_Type<T>::length = index;
else
{
Jupiter::String_Type<T>::length -= length;
length += index;
Jupiter::String_Type<T>::str[index] = Jupiter::String_Type<T>::str[length];
while (++index != Jupiter::String_Type<T>::length)
Jupiter::String_Type<T>::str[index] = Jupiter::String_Type<T>::str[++length];
}
}
// processEscapeSequences
template<typename T> void Jupiter::String_Type<T>::processEscapeSequences()
{
}
template<> inline void Jupiter::String_Type<char>::processEscapeSequences()
{
if (Jupiter::String_Type<char>::length == 0)
return;
size_t index = 0;
while (index + 1 != Jupiter::String_Type<char>::length)
{
printf("Processing: %c (%u) @ %u" ENDL, this->get(index), this->get(index), index);
if (this->get(index) == '\\')
{
switch (this->get(++index))
{
case '0':
case '1':
case '2':
case '3':
if (index + 1 != Jupiter::String_Type<char>::length && Jupiter_isBase(this->get(index + 1), 8))
{
if (index + 2 != Jupiter::String_Type<char>::length && Jupiter_isBase(this->get(index + 2), 8))
this->replace(index - 1, 4, static_cast<uint8_t>(Jupiter_getBase(this->get(index), 8)) << 6 | static_cast<uint8_t>(Jupiter_getBase(this->get(index + 1), 8)) << 3 | static_cast<uint8_t>(Jupiter_getBase(this->get(index + 2), 8)));
else
this->replace(index - 1, 3, static_cast<uint8_t>(Jupiter_getBase(this->get(index), 8)) << 3 | static_cast<uint8_t>(Jupiter_getBase(this->get(index + 1), 8)));
}
else
this->replace(index - 1, 2, static_cast<uint8_t>(Jupiter_getBase(this->get(index), 8)));
break;
case '4':
case '5':
case '6':
case '7':
if (index + 1 != Jupiter::String_Type<char>::length && Jupiter_isBase(this->get(index + 1), 8))
this->replace(index - 1, 3, static_cast<uint8_t>(Jupiter_getBase(this->get(index), 8)) << 3 | static_cast<uint8_t>(Jupiter_getBase(this->get(index + 1), 8)));
else
this->replace(index - 1, 2, static_cast<uint8_t>(Jupiter_getBase(this->get(index), 8)));
break;
case 'a':
this->replace(index - 1, 2, '\a');
break;
case 'b':
this->replace(index - 1, 2, '\b');
break;
case 'f':
this->replace(index - 1, 2, '\f');
break;
case 'n':
this->replace(index - 1, 2, '\n');
break;
case 'r':
this->replace(index - 1, 2, '\r');
break;
case 't':
this->replace(index - 1, 2, '\t');
break;
case 'v':
this->replace(index - 1, 2, '\v');
break;
case '?':
this->replace(index - 1, 2, '\?');
break;
case '\'':
this->replace(index - 1, 2, '\'');
break;
case '\"':
this->replace(index - 1, 2, '\"');
break;
case '\\':
this->replace(index - 1, 2, '\\');
break;
case 'x':
if (Jupiter::String_Type<char>::length >= index + 2
&& Jupiter_isBase(this->get(index + 1), 16) && Jupiter_isBase(this->get(index + 2), 16))
this->replace(index - 1, 4, static_cast<uint8_t>(Jupiter_getBase(this->get(index + 1), 16)) << 4 | static_cast<uint8_t>(Jupiter_getBase(this->get(index + 2), 16)));
break;
case 'U':
if (Jupiter::String_Type<char>::length >= index + 8
&& Jupiter_isBase(this->get(index + 1), 16) && Jupiter_isBase(this->get(index + 2), 16) && Jupiter_isBase(this->get(index + 3), 16) && Jupiter_isBase(this->get(index + 4), 16) && Jupiter_isBase(this->get(index + 5), 16) && Jupiter_isBase(this->get(index + 6), 16) && Jupiter_isBase(this->get(index + 7), 16) && Jupiter_isBase(this->get(index + 8), 16))
{
uint32_t codepoint = static_cast<uint8_t>(Jupiter_getBase(this->get(index + 1), 16)) << 4 | static_cast<uint8_t>(Jupiter_getBase(this->get(index + 2), 16));
codepoint <<= 8;
codepoint |= static_cast<uint8_t>(Jupiter_getBase(this->get(index + 3), 16)) << 4 | static_cast<uint8_t>(Jupiter_getBase(this->get(index + 4), 16));
codepoint <<= 8;
codepoint |= static_cast<uint8_t>(Jupiter_getBase(this->get(index + 5), 16)) << 4 | static_cast<uint8_t>(Jupiter_getBase(this->get(index + 6), 16));
codepoint <<= 8;
codepoint |= static_cast<uint8_t>(Jupiter_getBase(this->get(index + 7), 16)) << 4 | static_cast<uint8_t>(Jupiter_getBase(this->get(index + 8), 16));
if (codepoint <= 0x007F)
this->replace(index - 1, 10, static_cast<uint8_t>(codepoint));
else if (codepoint <= 0x07FF)
{
char bytes[2];
bytes[0] = 0xC0 | ((codepoint >> 6) & 0x1F);
bytes[1] = 0x80 | (codepoint & 0x3F);
this->replace(index - 1, 10, bytes, sizeof(bytes));
++index;
}
else if (codepoint <= 0xFFFF)
{
char bytes[3];
bytes[0] = 0xE0 | ((codepoint >> 12) & 0x0F);
bytes[1] = 0x80 | ((codepoint >> 6) & 0x3F);
bytes[2] = 0x80 | (codepoint & 0x3F);
this->replace(index - 1, 10, bytes, sizeof(bytes));
index += 2;
}
else if (codepoint <= 0x10FFFF)
{
char bytes[4];
bytes[0] = 0xE0 | ((codepoint >> 18) & 0x0F);
bytes[1] = 0x80 | ((codepoint >> 12) & 0x3F);
bytes[2] = 0x80 | ((codepoint >> 6) & 0x3F);
bytes[3] = 0x80 | (codepoint & 0x3F);
this->replace(index - 1, 10, bytes, sizeof(bytes));
index += 3;
}
}
break;
case 'u':
if (Jupiter::String_Type<char>::length >= index + 4
&& Jupiter_isBase(this->get(index + 1), 16) && Jupiter_isBase(this->get(index + 2), 16) && Jupiter_isBase(this->get(index + 3), 16) && Jupiter_isBase(this->get(index + 4), 16))
{
uint16_t codepoint = static_cast<uint8_t>(Jupiter_getBase(this->get(index + 1), 16)) << 4 | static_cast<uint8_t>(Jupiter_getBase(this->get(index + 2), 16));
codepoint <<= 8;
codepoint |= static_cast<uint8_t>(Jupiter_getBase(this->get(index + 3), 16)) << 4 | static_cast<uint8_t>(Jupiter_getBase(this->get(index + 4), 16));
if (codepoint <= 0x007F)
this->replace(index - 1, 6, static_cast<uint8_t>(codepoint));
else if (codepoint <= 0x07FF)
{
char bytes[2];
bytes[0] = 0xC0 | ((codepoint >> 6) & 0x1F);
bytes[1] = 0x80 | (codepoint & 0x3F);
this->replace(index - 1, 6, bytes, sizeof(bytes));
++index;
}
else if (codepoint <= 0xFFFF)
{
char bytes[3];
bytes[0] = 0xE0 | ((codepoint >> 12) & 0x0F);
bytes[1] = 0x80 | ((codepoint >> 6) & 0x3F);
bytes[2] = 0x80 | (codepoint & 0x3F);
this->replace(index - 1, 6, bytes, sizeof(bytes));
index += 2;
}
}
break;
default:
break;
}
if (index == Jupiter::String_Type<char>::length)
break;
}
else
++index;
}
}
template<> inline void Jupiter::String_Type<wchar_t>::processEscapeSequences()
{
}
// set // set
template<typename T> size_t Jupiter::String_Type<T>::set(size_t index, const T &in) template<typename T> size_t Jupiter::String_Type<T>::set(size_t index, const T &in)
{ {
if (index == this->size()) if (index == Jupiter::String_Type<T>::length)
return this->concat(in); return this->concat(in);
if (index > this->size()) if (index > Jupiter::String_Type<T>::length)
{ {
this->setBufferSize(index + 1); this->setBufferSize(index + 1);
while (Jupiter::String_Type<T>::length != index) while (Jupiter::String_Type<T>::length != index)
@ -152,10 +335,10 @@ template<typename T> size_t Jupiter::String_Type<T>::set(size_t index, const T &
template<typename T> size_t Jupiter::String_Type<T>::set(size_t index, const T *in, size_t inSize) template<typename T> size_t Jupiter::String_Type<T>::set(size_t index, const T *in, size_t inSize)
{ {
if (index == this->size()) if (index == Jupiter::String_Type<T>::length)
return this->concat(in); return this->concat(in);
if (index > this->size()) if (index > Jupiter::String_Type<T>::length)
{ {
this->setBufferSize(index + inSize); this->setBufferSize(index + inSize);
while (Jupiter::String_Type<T>::length != index) while (Jupiter::String_Type<T>::length != index)
@ -225,15 +408,15 @@ template<typename T> size_t Jupiter::String_Type<T>::set(const T &in)
return Jupiter::String_Type<T>::length = 1; return Jupiter::String_Type<T>::length = 1;
} }
// replace // insert
template<typename T> size_t Jupiter::String_Type<T>::insert(size_t index, const T &value) template<typename T> size_t Jupiter::String_Type<T>::insert(size_t index, const T &value)
{ {
if (index >= this->size()) if (index >= Jupiter::String_Type<T>::length)
return this->concat(value); return this->concat(value);
this->setBufferSize(this->size() + 1); this->setBufferSize(Jupiter::String_Type<T>::length + 1);
for (size_t i = this->size(); i != index; i--) for (size_t i = Jupiter::String_Type<T>::length; i != index; i--)
Jupiter::String_Type<T>::str[i] = this->get(i-1); Jupiter::String_Type<T>::str[i] = this->get(i-1);
Jupiter::String_Type<T>::str[index] = value; Jupiter::String_Type<T>::str[index] = value;
@ -242,7 +425,7 @@ template<typename T> size_t Jupiter::String_Type<T>::insert(size_t index, const
template<typename T> size_t Jupiter::String_Type<T>::insert(size_t index, const Jupiter::Readable_String<T> &value) template<typename T> size_t Jupiter::String_Type<T>::insert(size_t index, const Jupiter::Readable_String<T> &value)
{ {
if (index >= this->size()) if (index >= Jupiter::String_Type<T>::length)
return this->concat(value); return this->concat(value);
if (value.size() == 0) if (value.size() == 0)
@ -251,9 +434,9 @@ template<typename T> size_t Jupiter::String_Type<T>::insert(size_t index, const
if (value.size() == 1) if (value.size() == 1)
return this->insert(index, value.get(0)); return this->insert(index, value.get(0));
this->setBufferSize(this->size() + value.size()); this->setBufferSize(Jupiter::String_Type<T>::length + value.size());
size_t i; size_t i;
for (i = this->size() + value.size() - 1; i != index + value.size() - 1; i--) for (i = Jupiter::String_Type<T>::length + value.size() - 1; i != index + value.size() - 1; i--)
Jupiter::String_Type<T>::str[i] = this->get(i - value.size()); Jupiter::String_Type<T>::str[i] = this->get(i - value.size());
while (i != index) while (i != index)
@ -268,9 +451,99 @@ template<typename T> size_t Jupiter::String_Type<T>::insert(size_t index, const
// replace // replace
template<typename T> size_t Jupiter::String_Type<T>::replace(size_t index, size_t targetSize, const T &value)
{
if (targetSize != 0)
{
if (index >= Jupiter::String_Type<T>::length)
return this->set(index, value);
if (index + targetSize > Jupiter::String_Type<T>::length)
{
Jupiter::String_Type<T>::str[index] = value;
return Jupiter::String_Type<T>::length = index + 1;
}
if (targetSize == 1)
return this->set(index, value);
Jupiter::String_Type<T>::str[index] = value;
Jupiter::String_Type<T>::length -= targetSize - 1;
while (++index != Jupiter::String_Type<T>::length)
Jupiter::String_Type<T>::str[index] = Jupiter::String_Type<T>::str[index + targetSize - 1];
}
return Jupiter::String_Type<T>::length;
}
template<typename T> size_t Jupiter::String_Type<T>::replace(size_t index, size_t targetSize, const T *value, size_t valueSize)
{
if (valueSize == 1)
return this->replace(index, targetSize, *value);
if (valueSize == 0)
{
this->remove(index, targetSize);
return Jupiter::String_Type<T>::length;
}
if (targetSize != 0)
{
if (index >= Jupiter::String_Type<T>::length)
return this->set(index, value);
if (index + targetSize > Jupiter::String_Type<T>::length)
{
if (index + valueSize > Jupiter::String_Type<T>::length)
this->setBufferSize(index + valueSize);
Jupiter::String_Type<T>::length = index + valueSize;
Jupiter::String_Type<T>::str[index] = *value;
while (++index != Jupiter::String_Type<T>::length)
Jupiter::String_Type<T>::str[index] = *++value;
return Jupiter::String_Type<T>::length;
}
if (targetSize == valueSize)
return this->set(index, value, valueSize);
if (valueSize < targetSize)
{
targetSize -= valueSize;
Jupiter::String_Type<T>::length -= targetSize;
Jupiter::String_Type<T>::str[index] = *value;
while (--valueSize != 0)
Jupiter::String_Type<T>::str[++index] = *++value;
while (++index != Jupiter::String_Type<T>::length)
Jupiter::String_Type<T>::str[index] = Jupiter::String_Type<T>::str[index + targetSize];
}
else
{
this->setBufferSize(Jupiter::String_Type<T>::length + valueSize - targetSize);
Jupiter::String_Type<T>::length += valueSize - targetSize;
size_t i = Jupiter::String_Type<T>::length;
while (--i != index + targetSize + 1)
Jupiter::String_Type<T>::str[i] = Jupiter::String_Type<T>::str[i - valueSize + targetSize];
this->println(stdout);
Jupiter::String_Type<T>::str[index] = *value;
while (index != i)
Jupiter::String_Type<T>::str[++index] = *++value;
}
}
return Jupiter::String_Type<T>::length;
}
template<typename T> size_t Jupiter::String_Type<T>::replace(size_t index, size_t targetSize, const Jupiter::Readable_String<T> &value)
{
return this->replace(index, targetSize, value.ptr(), value.size());
}
template<typename T> size_t Jupiter::String_Type<T>::replace(const T &target, const T &value) template<typename T> size_t Jupiter::String_Type<T>::replace(const T &target, const T &value)
{ {
for (size_t i = 0; i != this->size(); i++) for (size_t i = 0; i != Jupiter::String_Type<T>::length; i++)
{ {
if (this->get(i) == target) if (this->get(i) == target)
Jupiter::String_Type<T>::str[i] = value; Jupiter::String_Type<T>::str[i] = value;
@ -285,10 +558,10 @@ template<typename T> size_t Jupiter::String_Type<T>::replace(const T *target, si
if (targetSize == 1) if (targetSize == 1)
return this->replace(*target, value); return this->replace(*target, value);
if (targetSize < this->size()) if (targetSize < Jupiter::String_Type<T>::length)
{ {
size_t i = 0, j = 0, k; size_t i = 0, j = 0, k;
while (j <= this->size() - targetSize) while (j <= Jupiter::String_Type<T>::length - targetSize)
{ {
k = 0; k = 0;
while (this->get(j + k) == target[k]) while (this->get(j + k) == target[k])
@ -304,12 +577,12 @@ template<typename T> size_t Jupiter::String_Type<T>::replace(const T *target, si
if (k != targetSize) if (k != targetSize)
Jupiter::String_Type<T>::str[i++] = Jupiter::String_Type<T>::str[j++]; Jupiter::String_Type<T>::str[i++] = Jupiter::String_Type<T>::str[j++];
} }
while (j < this->size()) while (j < Jupiter::String_Type<T>::length)
Jupiter::String_Type<T>::str[i++] = Jupiter::String_Type<T>::str[j++]; Jupiter::String_Type<T>::str[i++] = Jupiter::String_Type<T>::str[j++];
Jupiter::String_Type<T>::length = i; Jupiter::String_Type<T>::length = i;
} }
else if (targetSize == this->size() && this->equals(target, targetSize)) else if (targetSize == Jupiter::String_Type<T>::length && this->equals(target, targetSize))
return this->set(value); return this->set(value);
} }
return Jupiter::String_Type<T>::length; return Jupiter::String_Type<T>::length;
@ -330,7 +603,7 @@ template<typename T> size_t Jupiter::String_Type<T>::replace(const T *target, si
//if (targetSize == 1) //if (targetSize == 1)
// return this->replace(*target, value, valueSize); // return this->replace(*target, value, valueSize);
if (targetSize < this->size()) if (targetSize < Jupiter::String_Type<T>::length)
{ {
if (valueSize > targetSize) if (valueSize > targetSize)
{ {
@ -338,7 +611,7 @@ template<typename T> size_t Jupiter::String_Type<T>::replace(const T *target, si
size_t *instances = new size_t[instancesSize]; size_t *instances = new size_t[instancesSize];
// pass 1 (count instances) // pass 1 (count instances)
size_t instanceCount = 0, i = 0, j; size_t instanceCount = 0, i = 0, j;
while (i <= this->size() - targetSize) while (i <= Jupiter::String_Type<T>::length - targetSize)
{ {
j = 0; j = 0;
while (this->get(i + j) == target[j]) while (this->get(i + j) == target[j])
@ -367,7 +640,7 @@ template<typename T> size_t Jupiter::String_Type<T>::replace(const T *target, si
if (instanceCount != 0) if (instanceCount != 0)
{ {
// pass 2 (adjust string and replace values) // pass 2 (adjust string and replace values)
size_t endSize = this->size() + (valueSize - targetSize) * instanceCount; size_t endSize = Jupiter::String_Type<T>::length + (valueSize - targetSize) * instanceCount;
this->setBufferSize(endSize); this->setBufferSize(endSize);
instancesSize = endSize; // Repurposing. Now used as just another index. instancesSize = endSize; // Repurposing. Now used as just another index.
j = Jupiter::String_Type<T>::length; j = Jupiter::String_Type<T>::length;
@ -389,7 +662,7 @@ template<typename T> size_t Jupiter::String_Type<T>::replace(const T *target, si
else else
{ {
size_t i = 0, j = 0, k, l; size_t i = 0, j = 0, k, l;
while (j <= this->size() - targetSize) while (j <= Jupiter::String_Type<T>::length - targetSize)
{ {
k = 0; k = 0;
while (this->get(j + k) == target[k]) while (this->get(j + k) == target[k])
@ -406,13 +679,13 @@ template<typename T> size_t Jupiter::String_Type<T>::replace(const T *target, si
if (k != targetSize) if (k != targetSize)
Jupiter::String_Type<T>::str[i++] = Jupiter::String_Type<T>::str[j++]; Jupiter::String_Type<T>::str[i++] = Jupiter::String_Type<T>::str[j++];
} }
while (j < this->size()) while (j < Jupiter::String_Type<T>::length)
Jupiter::String_Type<T>::str[i++] = Jupiter::String_Type<T>::str[j++]; Jupiter::String_Type<T>::str[i++] = Jupiter::String_Type<T>::str[j++];
Jupiter::String_Type<T>::length = i; Jupiter::String_Type<T>::length = i;
} }
} }
else if (targetSize == this->size() && this->equals(target, targetSize)) else if (targetSize == Jupiter::String_Type<T>::length && this->equals(target, targetSize))
return this->set(value); return this->set(value);
} }
return Jupiter::String_Type<T>::length; return Jupiter::String_Type<T>::length;

BIN
Release/Jupiter.lib

Binary file not shown.
Loading…
Cancel
Save