STL string - converting to low case

V

Vadim

Hi!

I have a STL string, which I need to convert to low case.
In VC 6 I used:
string sInputBuffer = _strlwr((char*)sBuffer.c_str());

However, now in MSVC.NET 2005 I am getting a warning, that _strlwr is
depricated. Instead, it's proposed to use _strlwr_s :
http://msdn2.microsoft.com/en-us/library/y889wzfw.aspx

How should I use this new function with STL, if I don't want to
allocate memory on heap.

Thanks.

Vadim
 
I

int2str

Vadim said:
Hi!

I have a STL string, which I need to convert to low case.
In VC 6 I used:
string sInputBuffer = _strlwr((char*)sBuffer.c_str());

Try this maybe (std C++ - don't know about MVC):

std::transform( sBuffer.begin(), sBuffer.end(), sBuffer.begin(),
::tolower );

Cheers,
Andre
 
V

Victor Bazarov

Vadim said:
I have a STL string, which I need to convert to low case.
In VC 6 I used:
string sInputBuffer = _strlwr((char*)sBuffer.c_str());
Ugh!

However, now in MSVC.NET 2005 I am getting a warning, that _strlwr is
depricated. Instead, it's proposed to use _strlwr_s :
http://msdn2.microsoft.com/en-us/library/y889wzfw.aspx

How should I use this new function with STL, if I don't want to
allocate memory on heap.

http://groups.google.com/groups?q=convert+string+lowercase&qt_s=Search

V
 
R

roberts.noah

Vadim said:
Hi!

I have a STL string, which I need to convert to low case.
In VC 6 I used:
string sInputBuffer = _strlwr((char*)sBuffer.c_str());

However, now in MSVC.NET 2005 I am getting a warning, that _strlwr is
depricated. Instead, it's proposed to use _strlwr_s :
http://msdn2.microsoft.com/en-us/library/y889wzfw.aspx

How should I use this new function with STL, if I don't want to
allocate memory on heap.

Are you sure you need to convert to lower case? If all you want is
case insensitive comparison you might have a look at char_traits.
 
E

E. Mark Ping

string sInputBuffer = _strlwr((char*)sBuffer.c_str());

Ouch. I suggest you look up the definition of _strlwr.

Also, note that c_str() returns a non-modifiable c-style string.
 
A

atgraham

Try this:

struct lowercase_func {
void operator()(std::string::value_type& v) { v = tolower(v); }
};
std::string make_lowercase(std::string s) {
for_each(s.begin(), s.end(), lowercase_func());
return s;
}
 
R

Richard Herring

Try this:

struct lowercase_func {
void operator()(std::string::value_type& v) { v = tolower(v); }
};
std::string make_lowercase(std::string s) {
for_each(s.begin(), s.end(), lowercase_func());
return s;
}
But for_each is intended to be a non-modifying operation. OK, it will
work, but std::transform(s.begin(), s.end(), s.begin(), tolower) would
more clearly express your intention.
 
E

Earl Purple

Are you sure you need to convert to lower case? If all you want is
case insensitive comparison you might have a look at char_traits.

and exactly which function of char_traits would you use to do that?
 
V

Vadim

Thanks for your help.
In fact, I do need to make some case insensitive finds, but since some
parts of my original string I will have to convert later to unified
case, I decieded to convert the original string to low case. It seems
that there is no any perfoamnce problem. 250 Kb file in my string is
converted to low case almost without seeing delay in "Step over"
debugging.

I do have perfomance problem with reading from file and I guess you can
help me:
I have a text file, which I read entirely to my string variable.
Originally I made some checks while reading, so my code looks like
that:

ifstream is;
is.open (INPUT_FILE);
string sInputBuffer;

while (is.good())
{
sInputBuffer+= is.get();
}

Now, I just only read the contents of the file to string buffer.
Reading char after char is definitely the bad thing. What would be the
most efficient way of reading the whole file?

Thanks a lot!

Vadim
 
R

roberts.noah

Richard said:
But for_each is intended to be a non-modifying operation. OK, it will
work, but std::transform(s.begin(), s.end(), s.begin(), tolower) would
more clearly express your intention.

Except transform does not modify the original, for_each does (so I
don's see how you can make that first statement actually). You can use
transform to modify like above but it is actually slower that using
for_each because you are copying AND assigning whereas for_each will
modify directly without either of those operations...although in this
particular case you do that anyway so it may be faster to use transform
and loose the extra call.

In every book I have ever seen for_each is listed as a modifying
algorithm along with transform, merge, fill, generate, etc... It is
perfectly legitimate to use it as such and quite common to do so.
 
R

Richard Herring

Except transform does not modify the original, for_each does (so I
don's see how you can make that first statement actually).

I make it because for_each appears in section 25.1.1 of the Standard at
25.1.1, the first sub-section of 25.1, "Non-modifying sequence
operations". The first two parameters of for_each are only required to
be input iterators and its "Effects" clause does not say that anything
pointed to by the iterators is modified.
You can use
transform to modify like above but it is actually slower that using
for_each because you are copying AND assigning whereas for_each will
modify directly without either of those operations...although in this
particular case you do that anyway so it may be faster to use transform
and loose the extra call.

In every book I have ever seen for_each is listed as a modifying
algorithm along with transform, merge, fill, generate, etc...

That might surprise the authors of the Standard.
It is
perfectly legitimate to use it as such

It's an obvious extension of the semantics required by the Standard,
provided that you pass parameters which happen to satisfy the
requirements of a mutable iterator. I'll leave it to the language
lawyers to argue whether that translates to "perfectly legitimate".
 
R

roberts.noah

Richard said:
In message <[email protected]>,
(e-mail address removed) writes

That might surprise the authors of the Standard.

Only if they have completely independent, dual personalities.

By "authors of the Standard" I assume you mean people who were on the
committee...if you are talking about the people that did the
typesetting I don't know, nor do I care, what surprises them or doesn't.
 
R

Richard Herring

Let's see...

How about Bjarne Stroustrup, "The C++ Programming language", Third
Edition, where for_each is described in section 18.5, "Nonmodifying
Sequence Algorithms" ? Granted, he goes on to explain how it can be used
as a modifying algorithm, but it's quite definitely in the nonmodifying
section of the relevant chapter.

Or Matthew H Austern, "Generic Programming and the STL", where for_each
is in chapter 11, "Nonmutating Algorithms"?
Only if they have completely independent, dual personalities.

By "authors of the Standard" I assume you mean people who were on the
committee...

I mean those who assigned for_each to the category of non-modifying
sequence operations in the Standard. And who make no reference in the
same standard to using it with anything other than forward iterators,
and no mention of it modifying the sequence.
if you are talking about the people that did the
typesetting I don't know, nor do I care, what surprises them or doesn't.
I don't believe typographical error is involved here.
 
E

Earl Purple

Only if they have completely independent, dual personalities.

By "authors of the Standard" I assume you mean people who were on the
committee...if you are talking about the people that did the
typesetting I don't know, nor do I care, what surprises them or doesn't.

If you really want a modifying for_each then write one.

template
<
typename InOutIter,
typename OpOp for_each2( InOutIter start, const InOutIter & end, Op op )
{
for( ; start != end ; ++start )
{
op( *start );
}
return op;
}

Not exactly difficult now was that.
 
R

rossum

Now, I just only read the contents of the file to string buffer.
Reading char after char is definitely the bad thing. What would be the
most efficient way of reading the whole file?

Look at getline(). It reads a whole line at a time.

rossum
 
E

Earl Purple

You don't need to.

Not with most implementations but according to the standard, someone
might implement for_each to not work in writable mode, in which case
there would be a need to.
I really fail to understand what call there was for that.

By the way you still haven't answered my post above on how you would
implement case-insensitive lookup using char_traits.
 
D

Daniel T.

Richard Herring said:
Let's see...

How about Bjarne Stroustrup, "The C++ Programming language", Third
Edition, where for_each is described in section 18.5, "Nonmodifying
Sequence Algorithms" ? Granted, he goes on to explain how it can be used
as a modifying algorithm, but it's quite definitely in the nonmodifying
section of the relevant chapter.

Let's do that...

The for_each() algorithm is classified as nonmodifying because it
doesn't explicitly modify a sequence. However, if applied to a
non-const sequence for_each()'s operation (its third argument) may
change the elements of the sequence."

He even gives an example. Hummm...

You see, a "modifying" algorithm is called such because it explicitly
changes some sequence, not because it allows a sequence to be changed.
 
R

Richard Herring

Let's do that...

The for_each() algorithm is classified as nonmodifying because it
doesn't explicitly modify a sequence. However, if applied to a
non-const sequence for_each()'s operation (its third argument) may
change the elements of the sequence."

He even gives an example. Hummm...

You see, a "modifying" algorithm is called such because it explicitly
changes some sequence, not because it allows a sequence to be changed.

Right. So according to that definition too, for_each is not a modifying
algorithm.
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

No members online now.

Forum statistics

Threads
474,432
Messages
2,571,680
Members
48,796
Latest member
Greg L.

Latest Threads

Top