String Helpers

1. The output from the character trim is not what was expected.
Expected: "this % needs a lot\rof trimming" but got "of trimmings a lot" Similarly, trimleft and trimright does not work. How come?

2. The statement inline std::vector<tstring<CharT>> split(tstring<CharT> text, CharT const delimiter) has a red squiggly line under the left angle bracket after vector. The statement looks correct. Why is this happening?


cpp file
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
#include "string library.h"
#include <iostream>

int main()
{
	using namespace std::string_literals;

	auto ut{ string_library::to_upper("this is not UPPERCASE"s) };
	// ut = "THIS IS NOT UPPERCASE"
	std::cout << "to_upper: " << ut << std::endl;

	auto lt{ string_library::to_lower("THIS IS NOT lowercase"s) };
	// lt = "this is not lowercase"
	std::cout << "to_lower: " << lt << std::endl;

	auto rt{ string_library::reverse("cookbook"s) }; // rt = "koobkooc"
	std::cout << "reverse: " << rt << std::endl;

	auto text1{ "   this is an example   "s };
	auto t1{ string_library::trim(text1) };      // t1 = "this is an example"
	std::cout << "trim both ends: " << t1 << std::endl;

	auto t2{ string_library::trimleft(text1) };  // t2 = "this is an example   "
	std::cout << "trim left: " << t2 << std::endl;

	auto t3{ string_library::trimright(text1) }; // t3 = "   this is an example"
	std::cout << "trim right: " << t3 << std::endl;

	std::cout << std::endl << std::endl << std::endl;
	auto chars1{ " !%\n\r"s };
	auto text3{ "!!  this % needs a lot\rof trimming  !\n"s };
	auto t7{ string_library::trim(text3, chars1) };
	// t7 = "this % needs a lot\rof trimming"
	std::cout << "t7: " << std::endl;
	std::cout << t7 << std::endl;

	auto t8{ string_library::trimleft(text3, chars1) };
	// t8 = "this % needs a lot\rof trimming  !\n"
	std::cout << "t8: " << std::endl;
	std::cout << t8 << std::endl;

	auto t9{ string_library::trimright(text3, chars1) };
	// t9 = "!!  this % needs a lot\rof trimming"
	std::cout << "t9: " << std::endl;
	std::cout << t9 << std::endl;
	
	auto text4{ "must remove all * from text**"s };
	auto t10{ string_library::remove(text4, '*') };
	std::cout << "t10: " << t10 << std::endl;

	auto t11{ string_library::remove(text4, '!') };
	std::cout << "t11: " << t11 << std::endl;

	auto text5{ "this text will be split   "s };
	auto tokens1{ string_library::split(text5, ' ') };
	// tokens1 = {"this", "text", "will", "be", "split"}

	auto tokens2{ string_library::split(""s, ' ') };
	// tokens2 = {}

	system("pause");
	return 0;
}


header file
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
#pragma once

#include <string>
#include <algorithm>

namespace string_library
{
	template <typename CharT>
	using tstring = std::basic_string<CharT, std::char_traits<CharT>,
		std::allocator<CharT>>;

	template <typename CharT>
	using tstringstream = std::basic_stringstream<CharT, std::char_traits<CharT>,
		std::allocator<CharT>>;

	template<typename CharT>
	inline tstring<CharT> to_upper(tstring<CharT> text)
	{
		std::transform(std::begin(text), std::end(text), std::begin(text), toupper);
		return text;
	}

	template<typename CharT>
	inline tstring<CharT> to_lower(tstring<CharT> text)
	{
		std::transform(std::begin(text), std::end(text), std::begin(text), tolower);
		return text;
	}

	template<typename CharT>
	inline tstring<CharT> reverse(tstring<CharT> text)
	{
		std::reverse(std::begin(text), std::end(text));
		return text;
	}

	template<typename CharT>
	inline tstring<CharT> trim(tstring<CharT> const & text)
	{
		auto first{ text.find_first_not_of(' ') };
		auto last{ text.find_last_not_of(' ') };
		return text.substr(first, (last - first + 1));
	}

	template<typename CharT>
	inline tstring<CharT> trimleft(tstring<CharT> const & text)
	{
		auto first{ text.find_first_not_of(' ') };
		return text.substr(first, text.size() - first);
	}

	template<typename CharT>
	inline tstring<CharT> trimright(tstring<CharT> const & text)
	{
		auto last{ text.find_last_not_of(' ') };
		return text.substr(0, last + 1);
	}

		template<typename CharT>
		inline tstring<CharT> trim(tstring<CharT> const & text, tstring<CharT> const & chars)
		{
			auto first{ text.find_first_not_of(chars) };
			auto last{ text.find_last_not_of(chars) };
			return text.substr(first, (last - first + 1));
		}

		template<typename CharT>
		inline tstring<CharT> trimleft(tstring<CharT> const & text, tstring<CharT> const & chars)
		{
			auto first{ text.find_first_not_of(chars) };
			return text.substr(first, text.size() - first);
		}

		template<typename CharT>
		inline tstring<CharT> trimright(tstring<CharT> const & text, tstring<CharT> const & chars)
		{
			auto last{ text.find_last_not_of(chars) };
			return text.substr(0, last + 1);
		}

		template<typename CharT>
		inline tstring<CharT> remove(tstring<CharT> text, CharT const ch)
		{
			auto start = std::remove_if(std::begin(text), std::end(text), [=](CharT const c) {return c == ch; });
			text.erase(start, std::end(text));
			return text;
		}

		template<typename CharT>
		inline std::vector<tstring<CharT>> split(tstring<CharT> text, CharT const delimiter)
		{
			auto sstr = tstringstream<CharT>{ text };
			auto tokens = std::vector<tstring<CharT>>{};
			auto token = tstring<CharT>{};
			while (std::getline(sstr, token, delimiter))
			{
				if (!token.empty()) tokens.push_back(token);
			}
			return tokens;
		}

}

1. The output from the character trim is not what was expected.
Expected: "this % needs a lot\rof trimming" but got "of trimmings a lot"

The character ‘carriage return’ (‘\r’) causes the cursor to get back to the beginning of the sentence while printing. Part of the answer is overwritten.
Just turn your std::string “text3” from
auto text3{ "!! this % needs a lot\rof trimming !\n"s };
to
auto text3{ "!! this % needs a lot of trimming !\n"s };
to get a good output.

2. The statement inline std::vector<tstring<CharT>> split(tstring<CharT> text, CharT const delimiter) has a red squiggly line under the left angle bracket after vector. The statement looks correct. Why is this happening?

It seems you forgot to include both <vector> and <sstream>.

The "trim" functions did what it was supposed to. It is when printing to the console the /r is executed.

Added <vector> and <sstream> and the program compiled and executed.


Thanks Enoizat!
Topic archived. No new replies allowed.