Browse Source

Hid append methods.

David Piuva 5 years ago
parent
commit
72cf6d6981

+ 6 - 6
Source/DFPSR/api/imageAPI.cpp

@@ -472,17 +472,17 @@ String dsr::image_toAscii(const ImageU8& image, const String& alphabet) {
 		alphabetMap[rawValue] = alphabet[charIndex];
 		alphabetMap[rawValue] = alphabet[charIndex];
 		output += scale;
 		output += scale;
 	}
 	}
-	result.appendChar(U'<');
+	string_appendChar(result, U'<');
 	for (int charIndex = 0; charIndex < alphabetSize; charIndex++) {
 	for (int charIndex = 0; charIndex < alphabetSize; charIndex++) {
-		result.appendChar(alphabet[charIndex]);
+		string_appendChar(result, alphabet[charIndex]);
 	}
 	}
-	result.append(U">\n");
+	string_append(result, U">\n");
 	for (int y = 0; y < height; y++) {
 	for (int y = 0; y < height; y++) {
-		result.appendChar(U'<');
+		string_appendChar(result, U'<');
 		for (int x = 0; x < width; x++) {
 		for (int x = 0; x < width; x++) {
-			result.appendChar(alphabetMap[image_readPixel_clamp(image, x, y)]);
+			string_appendChar(result, alphabetMap[image_readPixel_clamp(image, x, y)]);
 		}
 		}
-		result.append(U">\n");
+		string_append(result, U">\n");
 	}
 	}
 	return result;
 	return result;
 }
 }

+ 67 - 61
Source/DFPSR/base/text.cpp

@@ -33,6 +33,11 @@
 
 
 using namespace dsr;
 using namespace dsr;
 
 
+static void atomic_append(String &target, const char* source);
+static void atomic_append(String &target, const ReadableString& source);
+static void atomic_append(String &target, const char32_t* source);
+static void atomic_append(String &target, const std::string& source);
+
 static int64_t strlen_utf32(const char32_t *content) {
 static int64_t strlen_utf32(const char32_t *content) {
 	int64_t length = 0;
 	int64_t length = 0;
 	while (content[length] != 0) {
 	while (content[length] != 0) {
@@ -82,9 +87,9 @@ static String createSubString_shared(const DsrChar *content, int64_t length, con
 }
 }
 
 
 String::String() {}
 String::String() {}
-String::String(const char* source) { this->append(source); }
-String::String(const char32_t* source) { this->append(source); }
-String::String(const std::string& source) { this->append(source); }
+String::String(const char* source) { atomic_append(*this, source); }
+String::String(const char32_t* source) { atomic_append(*this, source); }
+String::String(const std::string& source) { atomic_append(*this, source); }
 String::String(const String& source) {
 String::String(const String& source) {
 	// Share immutable buffer
 	// Share immutable buffer
 	this->readSection = source.readSection;
 	this->readSection = source.readSection;
@@ -100,7 +105,7 @@ String::String(const ReadableString& source) {
 		this->writeSection = const_cast<char32_t*>(source.readSection); // Still safe because of immutability
 		this->writeSection = const_cast<char32_t*>(source.readSection); // Still safe because of immutability
 	} else {
 	} else {
 		// No buffer to share, just appending the content
 		// No buffer to share, just appending the content
-		this->append(source);
+		atomic_append(*this, source);
 	}
 	}
 }
 }
 
 
@@ -190,7 +195,7 @@ String dsr::string_upperCase(const ReadableString &text) {
 	String result;
 	String result;
 	string_reserve(result, text.length);
 	string_reserve(result, text.length);
 	for (int64_t i = 0; i < text.length; i++) {
 	for (int64_t i = 0; i < text.length; i++) {
-		result.appendChar(towupper(text[i]));
+		string_appendChar(result, towupper(text[i]));
 	}
 	}
 	return result;
 	return result;
 }
 }
@@ -199,7 +204,7 @@ String dsr::string_lowerCase(const ReadableString &text) {
 	String result;
 	String result;
 	string_reserve(result, text.length);
 	string_reserve(result, text.length);
 	for (int64_t i = 0; i < text.length; i++) {
 	for (int64_t i = 0; i < text.length; i++) {
-		result.appendChar(towlower(text[i]));
+		string_appendChar(result, towlower(text[i]));
 	}
 	}
 	return result;
 	return result;
 }
 }
@@ -240,34 +245,34 @@ ReadableString dsr::string_removeOuterWhiteSpace(const ReadableString &text) {
 String dsr::string_mangleQuote(const ReadableString &rawText) {
 String dsr::string_mangleQuote(const ReadableString &rawText) {
 	String result;
 	String result;
 	string_reserve(result, rawText.length + 2);
 	string_reserve(result, rawText.length + 2);
-	result.appendChar(U'\"'); // Begin quote
+	string_appendChar(result, U'\"'); // Begin quote
 	for (int64_t i = 0; i < rawText.length; i++) {
 	for (int64_t i = 0; i < rawText.length; i++) {
 		DsrChar c = rawText[i];
 		DsrChar c = rawText[i];
 		if (c == U'\"') { // Double quote
 		if (c == U'\"') { // Double quote
-			result.append(U"\\\"");
+			string_append(result, U"\\\"");
 		} else if (c == U'\\') { // Backslash
 		} else if (c == U'\\') { // Backslash
-			result.append(U"\\\\");
+			string_append(result, U"\\\\");
 		} else if (c == U'\a') { // Audible bell
 		} else if (c == U'\a') { // Audible bell
-			result.append(U"\\a");
+			string_append(result, U"\\a");
 		} else if (c == U'\b') { // Backspace
 		} else if (c == U'\b') { // Backspace
-			result.append(U"\\b");
+			string_append(result, U"\\b");
 		} else if (c == U'\f') { // Form feed
 		} else if (c == U'\f') { // Form feed
-			result.append(U"\\f");
+			string_append(result, U"\\f");
 		} else if (c == U'\n') { // Line feed
 		} else if (c == U'\n') { // Line feed
-			result.append(U"\\n");
+			string_append(result, U"\\n");
 		} else if (c == U'\r') { // Carriage return
 		} else if (c == U'\r') { // Carriage return
-			result.append(U"\\r");
+			string_append(result, U"\\r");
 		} else if (c == U'\t') { // Horizontal tab
 		} else if (c == U'\t') { // Horizontal tab
-			result.append(U"\\t");
+			string_append(result, U"\\t");
 		} else if (c == U'\v') { // Vertical tab
 		} else if (c == U'\v') { // Vertical tab
-			result.append(U"\\v");
+			string_append(result, U"\\v");
 		} else if (c == U'\0') { // Null terminator
 		} else if (c == U'\0') { // Null terminator
-			result.append(U"\\0");
+			string_append(result, U"\\0");
 		} else {
 		} else {
-			result.appendChar(c);
+			string_appendChar(result, c);
 		}
 		}
 	}
 	}
-	result.appendChar(U'\"'); // End quote
+	string_appendChar(result, U'\"'); // End quote
 	return result;
 	return result;
 }
 }
 
 
@@ -283,25 +288,25 @@ String dsr::string_unmangleQuote(const ReadableString& mangledText) {
 			if (c == U'\\') { // Escape character
 			if (c == U'\\') { // Escape character
 				DsrChar c2 = mangledText[i + 1];
 				DsrChar c2 = mangledText[i + 1];
 				if (c2 == U'\"') { // Double quote
 				if (c2 == U'\"') { // Double quote
-					result.appendChar(U'\"');
+					string_appendChar(result, U'\"');
 				} else if (c2 == U'\\') { // Back slash
 				} else if (c2 == U'\\') { // Back slash
-					result.appendChar(U'\\');
+					string_appendChar(result, U'\\');
 				} else if (c2 == U'a') { // Audible bell
 				} else if (c2 == U'a') { // Audible bell
-					result.appendChar(U'\a');
+					string_appendChar(result, U'\a');
 				} else if (c2 == U'b') { // Backspace
 				} else if (c2 == U'b') { // Backspace
-					result.appendChar(U'\b');
+					string_appendChar(result, U'\b');
 				} else if (c2 == U'f') { // Form feed
 				} else if (c2 == U'f') { // Form feed
-					result.appendChar(U'\f');
+					string_appendChar(result, U'\f');
 				} else if (c2 == U'n') { // Line feed
 				} else if (c2 == U'n') { // Line feed
-					result.appendChar(U'\n');
+					string_appendChar(result, U'\n');
 				} else if (c2 == U'r') { // Carriage return
 				} else if (c2 == U'r') { // Carriage return
-					result.appendChar(U'\r');
+					string_appendChar(result, U'\r');
 				} else if (c2 == U't') { // Horizontal tab
 				} else if (c2 == U't') { // Horizontal tab
-					result.appendChar(U'\t');
+					string_appendChar(result, U'\t');
 				} else if (c2 == U'v') { // Vertical tab
 				} else if (c2 == U'v') { // Vertical tab
-					result.appendChar(U'\v');
+					string_appendChar(result, U'\v');
 				} else if (c2 == U'0') { // Null terminator
 				} else if (c2 == U'0') { // Null terminator
-					result.appendChar(U'\0');
+					string_appendChar(result, U'\0');
 				}
 				}
 				i++; // Consume both characters
 				i++; // Consume both characters
 			} else {
 			} else {
@@ -323,7 +328,7 @@ String dsr::string_unmangleQuote(const ReadableString& mangledText) {
 				} else if (c == U'\0') { // Null terminator
 				} else if (c == U'\0') { // Null terminator
 					 throwError(U"Unmangled null terminator detected in string_unmangleQuote!\n", mangledText, "\n");
 					 throwError(U"Unmangled null terminator detected in string_unmangleQuote!\n", mangledText, "\n");
 				} else {
 				} else {
-					result.appendChar(c);
+					string_appendChar(result, c);
 				}
 				}
 			}
 			}
 		}
 		}
@@ -336,7 +341,7 @@ static void uintToString_arabic(String& target, uint64_t value) {
 	DsrChar digits[bufferSize];
 	DsrChar digits[bufferSize];
 	int64_t usedSize = 0;
 	int64_t usedSize = 0;
 	if (value == 0) {
 	if (value == 0) {
-		target.appendChar(U'0');
+		string_appendChar(target, U'0');
 	} else {
 	} else {
 		while (usedSize < bufferSize) {
 		while (usedSize < bufferSize) {
 			DsrChar digit = U'0' + (value % 10u);
 			DsrChar digit = U'0' + (value % 10u);
@@ -349,7 +354,7 @@ static void uintToString_arabic(String& target, uint64_t value) {
 		}
 		}
 		while (usedSize > 0) {
 		while (usedSize > 0) {
 			usedSize--;
 			usedSize--;
-			target.appendChar(digits[usedSize]);
+			string_appendChar(target, digits[usedSize]);
 		}
 		}
 	}
 	}
 }
 }
@@ -358,7 +363,7 @@ static void intToString_arabic(String& target, int64_t value) {
 	if (value >= 0) {
 	if (value >= 0) {
 		uintToString_arabic(target, (uint64_t)value);
 		uintToString_arabic(target, (uint64_t)value);
 	} else {
 	} else {
-		target.appendChar(U'-');
+		string_appendChar(target, U'-');
 		uintToString_arabic(target, (uint64_t)(-value));
 		uintToString_arabic(target, (uint64_t)(-value));
 	}
 	}
 }
 }
@@ -384,7 +389,7 @@ static void doubleToString_arabic(String& target, double value) {
 		}
 		}
 	}
 	}
 	for (int64_t c = 0; c <= lastValueIndex; c++) {
 	for (int64_t c = 0; c <= lastValueIndex; c++) {
-		target.appendChar(result[c]);
+		string_appendChar(target, result[c]);
 	}
 	}
 }
 }
 
 
@@ -533,7 +538,7 @@ String dsr::string_loadFromMemory(Buffer fileContent) {
 	string_reserve(result, characterCount);
 	string_reserve(result, characterCount);
 	// Stream output to the result string
 	// Stream output to the result string
 	UTF32WriterFunction reciever = [&result](DsrChar character) {
 	UTF32WriterFunction reciever = [&result](DsrChar character) {
-		result.appendChar(character);
+		string_appendChar(result, character);
 	};
 	};
 	feedStringFromFileBuffer(reciever, buffer_dangerous_getUnsafeData(fileContent), buffer_getSize(fileContent));
 	feedStringFromFileBuffer(reciever, buffer_dangerous_getUnsafeData(fileContent), buffer_getSize(fileContent));
 	return result;
 	return result;
@@ -772,9 +777,9 @@ static void expand(String &target, int64_t newLength, bool affectUsedLength) {
 		if (newLength > getCapacity(target)) {
 		if (newLength > getCapacity(target)) {
 			reallocateBuffer(target, newLength, true);
 			reallocateBuffer(target, newLength, true);
 		}
 		}
-	}
-	if (affectUsedLength) {
-		target.length = newLength;
+		if (affectUsedLength) {
+			target.length = newLength;
+		}
 	}
 	}
 }
 }
 
 
@@ -803,83 +808,84 @@ void dsr::string_reserve(String& target, int64_t minimumLength) {
 	} \
 	} \
 }
 }
 // TODO: See if ascii litterals can be checked for values above 127 in compile-time
 // TODO: See if ascii litterals can be checked for values above 127 in compile-time
-void String::append(const char* source) { APPEND(*this, source, strlen(source), 0xFF); }
+static void atomic_append(String &target, const char* source) { APPEND(target, source, strlen(source), 0xFF); }
 // TODO: Use memcpy when appending input of the same format
 // TODO: Use memcpy when appending input of the same format
-void String::append(const ReadableString& source) { APPEND(*this, source, source.length, 0xFFFFFFFF); }
-void String::append(const char32_t* source) { APPEND(*this, source, strlen_utf32(source), 0xFFFFFFFF); }
-void String::append(const std::string& source) { APPEND(*this, source.c_str(), (int64_t)source.size(), 0xFF); }
-void String::appendChar(DsrChar source) { APPEND(*this, &source, 1, 0xFFFFFFFF); }
+static void atomic_append(String &target, const ReadableString& source) { APPEND(target, source, source.length, 0xFFFFFFFF); }
+static void atomic_append(String &target, const char32_t* source) { APPEND(target, source, strlen_utf32(source), 0xFFFFFFFF); }
+static void atomic_append(String &target, const std::string& source) { APPEND(target, source.c_str(), (int64_t)source.size(), 0xFF); }
+
+void dsr::string_appendChar(String& target, DsrChar value) { APPEND(target, &value, 1, 0xFFFFFFFF); }
 
 
 String& dsr::string_toStreamIndented(String& target, const Printable& source, const ReadableString& indentation) {
 String& dsr::string_toStreamIndented(String& target, const Printable& source, const ReadableString& indentation) {
 	return source.toStreamIndented(target, indentation);
 	return source.toStreamIndented(target, indentation);
 }
 }
 String& dsr::string_toStreamIndented(String& target, const char* value, const ReadableString& indentation) {
 String& dsr::string_toStreamIndented(String& target, const char* value, const ReadableString& indentation) {
-	target.append(indentation);
-	target.append(value);
+	atomic_append(target, indentation);
+	atomic_append(target, value);
 	return target;
 	return target;
 }
 }
 String& dsr::string_toStreamIndented(String& target, const ReadableString& value, const ReadableString& indentation) {
 String& dsr::string_toStreamIndented(String& target, const ReadableString& value, const ReadableString& indentation) {
-	target.append(indentation);
-	target.append(value);
+	atomic_append(target, indentation);
+	atomic_append(target, value);
 	return target;
 	return target;
 }
 }
 String& dsr::string_toStreamIndented(String& target, const char32_t* value, const ReadableString& indentation) {
 String& dsr::string_toStreamIndented(String& target, const char32_t* value, const ReadableString& indentation) {
-	target.append(indentation);
-	target.append(value);
+	atomic_append(target, indentation);
+	atomic_append(target, value);
 	return target;
 	return target;
 }
 }
 String& dsr::string_toStreamIndented(String& target, const std::string& value, const ReadableString& indentation) {
 String& dsr::string_toStreamIndented(String& target, const std::string& value, const ReadableString& indentation) {
-	target.append(indentation);
-	target.append(value);
+	atomic_append(target, indentation);
+	atomic_append(target, value);
 	return target;
 	return target;
 }
 }
 String& dsr::string_toStreamIndented(String& target, const float& value, const ReadableString& indentation) {
 String& dsr::string_toStreamIndented(String& target, const float& value, const ReadableString& indentation) {
-	target.append(indentation);
+	atomic_append(target, indentation);
 	doubleToString_arabic(target, (double)value);
 	doubleToString_arabic(target, (double)value);
 	return target;
 	return target;
 }
 }
 String& dsr::string_toStreamIndented(String& target, const double& value, const ReadableString& indentation) {
 String& dsr::string_toStreamIndented(String& target, const double& value, const ReadableString& indentation) {
-	target.append(indentation);
+	atomic_append(target, indentation);
 	doubleToString_arabic(target, value);
 	doubleToString_arabic(target, value);
 	return target;
 	return target;
 }
 }
 String& dsr::string_toStreamIndented(String& target, const int64_t& value, const ReadableString& indentation) {
 String& dsr::string_toStreamIndented(String& target, const int64_t& value, const ReadableString& indentation) {
-	target.append(indentation);
+	atomic_append(target, indentation);
 	intToString_arabic(target, value);
 	intToString_arabic(target, value);
 	return target;
 	return target;
 }
 }
 String& dsr::string_toStreamIndented(String& target, const uint64_t& value, const ReadableString& indentation) {
 String& dsr::string_toStreamIndented(String& target, const uint64_t& value, const ReadableString& indentation) {
-	target.append(indentation);
+	atomic_append(target, indentation);
 	uintToString_arabic(target, value);
 	uintToString_arabic(target, value);
 	return target;
 	return target;
 }
 }
 String& dsr::string_toStreamIndented(String& target, const int32_t& value, const ReadableString& indentation) {
 String& dsr::string_toStreamIndented(String& target, const int32_t& value, const ReadableString& indentation) {
-	target.append(indentation);
+	atomic_append(target, indentation);
 	intToString_arabic(target, (int64_t)value);
 	intToString_arabic(target, (int64_t)value);
 	return target;
 	return target;
 }
 }
 String& dsr::string_toStreamIndented(String& target, const uint32_t& value, const ReadableString& indentation) {
 String& dsr::string_toStreamIndented(String& target, const uint32_t& value, const ReadableString& indentation) {
-	target.append(indentation);
+	atomic_append(target, indentation);
 	uintToString_arabic(target, (uint64_t)value);
 	uintToString_arabic(target, (uint64_t)value);
 	return target;
 	return target;
 }
 }
 String& dsr::string_toStreamIndented(String& target, const int16_t& value, const ReadableString& indentation) {
 String& dsr::string_toStreamIndented(String& target, const int16_t& value, const ReadableString& indentation) {
-	target.append(indentation);
+	atomic_append(target, indentation);
 	intToString_arabic(target, (int64_t)value);
 	intToString_arabic(target, (int64_t)value);
 	return target;
 	return target;
 }
 }
 String& dsr::string_toStreamIndented(String& target, const uint16_t& value, const ReadableString& indentation) {
 String& dsr::string_toStreamIndented(String& target, const uint16_t& value, const ReadableString& indentation) {
-	target.append(indentation);
+	atomic_append(target, indentation);
 	uintToString_arabic(target, (uint64_t)value);
 	uintToString_arabic(target, (uint64_t)value);
 	return target;
 	return target;
 }
 }
 String& dsr::string_toStreamIndented(String& target, const int8_t& value, const ReadableString& indentation) {
 String& dsr::string_toStreamIndented(String& target, const int8_t& value, const ReadableString& indentation) {
-	target.append(indentation);
+	atomic_append(target, indentation);
 	intToString_arabic(target, (int64_t)value);
 	intToString_arabic(target, (int64_t)value);
 	return target;
 	return target;
 }
 }
 String& dsr::string_toStreamIndented(String& target, const uint8_t& value, const ReadableString& indentation) {
 String& dsr::string_toStreamIndented(String& target, const uint8_t& value, const ReadableString& indentation) {
-	target.append(indentation);
+	atomic_append(target, indentation);
 	uintToString_arabic(target, (uint64_t)value);
 	uintToString_arabic(target, (uint64_t)value);
 	return target;
 	return target;
 }
 }

+ 1 - 11
Source/DFPSR/base/text.h

@@ -123,14 +123,6 @@ public:
 	String(const std::string& source);
 	String(const std::string& source);
 	String(const ReadableString& source);
 	String(const ReadableString& source);
 	String(const String& source);
 	String(const String& source);
-public:
-	// Extend the String using more text
-	void append(const char* source);
-	void append(const ReadableString& source);
-	void append(const char32_t* source);
-	void append(const std::string& source);
-	// Extend the String using another character
-	void appendChar(DsrChar source);
 };
 };
 
 
 // Define this overload for non-virtual source types that cannot inherit from Printable
 // Define this overload for non-virtual source types that cannot inherit from Printable
@@ -330,9 +322,7 @@ int64_t string_getBufferUseCount(const ReadableString& text);
 void string_reserve(String& target, int64_t minimumLength);
 void string_reserve(String& target, int64_t minimumLength);
 
 
 // Append/push one character (to avoid integer to string conversion)
 // Append/push one character (to avoid integer to string conversion)
-inline void string_appendChar(String& target, DsrChar value) {
-	target.appendChar(value);
-}
+void string_appendChar(String& target, DsrChar value);
 
 
 // Append one element
 // Append one element
 template<typename TYPE>
 template<typename TYPE>

+ 7 - 7
Source/test/tests/StringTest.cpp

@@ -6,11 +6,11 @@
 //       Use "" operand as only constructor?
 //       Use "" operand as only constructor?
 void fooInPlace(dsr::String& target, const dsr::ReadableString& a, const dsr::ReadableString& b) {
 void fooInPlace(dsr::String& target, const dsr::ReadableString& a, const dsr::ReadableString& b) {
 	string_clear(target);
 	string_clear(target);
-	target.append(U"Foo(");
-	target.append(a);
-	target.appendChar(U',');
-	target.append(b);
-	target.appendChar(U')');
+	string_append(target, U"Foo(");
+	string_append(target, a);
+	string_appendChar(target, U',');
+	string_append(target, b);
+	string_appendChar(target, U')');
 }
 }
 
 
 dsr::String foo(const dsr::ReadableString& a, const dsr::ReadableString& b) {
 dsr::String foo(const dsr::ReadableString& a, const dsr::ReadableString& b) {
@@ -81,8 +81,8 @@ START_TEST(String)
 	{ // Processing
 	{ // Processing
 		dsr::String buffer = U"Garbage";
 		dsr::String buffer = U"Garbage";
 		ASSERT_MATCH(buffer, U"Garbage");
 		ASSERT_MATCH(buffer, U"Garbage");
-		buffer = foo(U"Ball", U"åäöÅÄÖ"); // Crash!
-		ASSERT_MATCH(buffer, U"Foo(Ball,åäöÅÄÖ)"); // Failed
+		buffer = foo(U"Ball", U"åäöÅÄÖ");
+		ASSERT_MATCH(buffer, U"Foo(Ball,åäöÅÄÖ)");
 		fooInPlace(buffer, U"Å", U"ф");
 		fooInPlace(buffer, U"Å", U"ф");
 		ASSERT_MATCH(buffer, U"Foo(Å,ф)");
 		ASSERT_MATCH(buffer, U"Foo(Å,ф)");
 	}
 	}