unique string

Started by
9 comments, last by _goat 16 years, 12 months ago
vector<char *c> v; input(char *c) { if(c not in vector) v.push_back(c);// let v contain un-repeated string. } but matter is: if address of string maybe different. but content of string is the same. so just push_back(c) is not correct. how to get a un-repeated string list?
Advertisement
use a real string... as in std::vector<std::string>

or, if you want a container of unique strings, std::set<std::string>
std::set<std::string> strings;void input(const std::string& str){  strings.insert(str); // set's elements are unique}
Either

A: Use a different container class, something that takes care of this for you. Or

B: Check each string in the vector against the string to be added, using a string compare function [like strcmp()] to determine if it's already in the vector. If you're taking this method, it's a good idea to order the strings in some fashion, so that you can reduce the time required to insert new elements. Effectively this will be reinventing the wheel, as this is pretty much exactly what stl::set does [not that there is anything wrong with reinventing the wheel for experience's sake, but just know that it's already out there and the code is already written.].

If you are going to use a set, either use a stl::string object [so that <, >, and ==, are overloaded], or provide a comparison function object to the type definition [like this this, stl::set<char*,compareObject>, with 'bool compareObject::operator()(char*,char*) defined].
yep, use a set<string>. char* is not a string type, it is a pointer type, and should almost never be found in your code as it is pretty rare to actually want a pointer to a char.
Quote:Original post by Drigovas
Either

If you are going to use a set, either use a stl::string object [so that <, >, and ==, are overloaded], or provide a comparison function object to the type definition [like this this, stl::set<char*,compareObject>, with 'bool compareObject::operator()(char*,char*) defined].

could you give me a sample for compareObject ?
Quote:Original post by 3dcgmodeling
Quote:Original post by Drigovas
Either

If you are going to use a set, either use a stl::string object [so that <, >, and ==, are overloaded], or provide a comparison function object to the type definition [like this this, stl::set<char*,compareObject>, with 'bool compareObject::operator()(char*,char*) defined].

could you give me a sample for compareObject ?


You could use the 'ltstr' demonstrated with SGI's documentation for std::set.

But be aware that you will still be responsible for the memory management for all the pointed-at text. There's no way around this; standard library containers clean up their memory and you are expected to clean up yours (because they don't really even know about it).
Quote:Original post by 3dcgmodeling
Quote:Original post by Drigovas
Either

If you are going to use a set, either use a stl::string object [so that <, >, and ==, are overloaded], or provide a comparison function object to the type definition [like this this, stl::set<char*,compareObject>, with 'bool compareObject::operator()(char*,char*) defined].

could you give me a sample for compareObject ?
Absolutely, consider the following
class LessThan{public:     bool operator()(int a, int b)//returns true if a is less than b     {          if( a < b )               return true;          else               return false;     }};


the operator (int,int) is overloaded, and can be used like this :

LessThan f;if(  f(1,2)  ){     ...}else{     ...}


It works in a way very similar to how a function works, once declared, except it allows you a bit more power, since you can include constructors, destructors, and any other sort of state information that is typical of classes. You would pass this class name to stl::set when you are creating it, like this:

class CompareTwoStrings{public:     bool operator()(char* a, char* b)     {           if(strcmp(a,b) < 0)                return true;           else                return false;     }};//now when defining the setstl::set<char*,CompareTwoStrings> aSetOfCharPointers;


When the set attempts to order it's elements, it will call the overloaded (char*,char*) operator defined in 'CompareTwoStrings' to determine the order that the elements go in. It will order it's elements starting with the element that returns 'true' most, as the first of the two variables provided [the first object reports true when compared with any other object in the set], and ending with the element that reports 'true' least, as the first of the two variables provided [the last element never reports true, regardless of what other object in the set it is compared with]. 'Equal' is determined if two elements, when compared, report 'false' regardless of what order they are compared in. Sets cannot have equal elements, so any entry where that requirement is met [compare(A,B) == false, and compare(B,A) == false] will flag the elements as equal, thus rejecting the entry.

Hope that's clear...If it isn't, I'd be happy to go into more detail into anything specific.
cool,I learn much from these, but my origin problem have not solved completely.



I test it ,and found even if I DO NOT use the CompareTwoStrings class,set will get unqiue string(with different char *pointer but content is the same).more set<char*> will get unique string other than unique pointer to char *. it is strang thing. anyone know it?
char *pchar[] ={		"abc45",		"abc9",		"abc3",		"abc4",		"abc5",};char *ctr[] ={	"abc4",	"abc3"};I found where is problem. if you define the above 2 array, you will found ctr and pchar share two the same address. what do you think of it,does compiler optimize it?

This topic is closed to new replies.

Advertisement