473,387 Members | 1,597 Online
Bytes | Software Development & Data Engineering Community
Post Job

Home Posts Topics Members FAQ

Join Bytes to post your question to a community of 473,387 software developers and data experts.

Efficient searching through stl map?

I have a std::map which consist of time_t as first and an associated class
as second:

map<time_t, myclass>

I would like to do calculations (min and max values) for a set of 'second'
for a specific time range.

Given the fact that 'first' can hold any time I would like to do the
calculation based on values which falls within a range of e.g. yesterday
(all 24 hours). So I'd like to efficiently find the first value of time_t
which meets this requirement.

Until now I've scanned forward by an iterator but if you have alot of values
this linear search becomes quite slow. This has become a problem to me. The
problem boils down to that I don't know the exact 'first' value that I'm
looking for but know within what timerange it should fall.

Are there any stl algorithms which can let me define my own compare
algorithm so I can do this time range checking in order to find the first
valid element? Naturally since time_t is just an integer the algorithm
should be faster then linear search.

Thanks in advance.

-- Henrik
Apr 9 '06 #1
3 3524
In article <44***********************@dread15.news.tele.dk> ,
"Henrik Goldman" <he************@mail.tele.dk> wrote:
I have a std::map which consist of time_t as first and an associated class
as second:

map<time_t, myclass>

I would like to do calculations (min and max values) for a set of 'second'
for a specific time range.

Given the fact that 'first' can hold any time I would like to do the
calculation based on values which falls within a range of e.g. yesterday
(all 24 hours). So I'd like to efficiently find the first value of time_t
which meets this requirement.

Until now I've scanned forward by an iterator but if you have alot of values
this linear search becomes quite slow. This has become a problem to me. The
problem boils down to that I don't know the exact 'first' value that I'm
looking for but know within what timerange it should fall.

Are there any stl algorithms which can let me define my own compare
algorithm so I can do this time range checking in order to find the first
valid element? Naturally since time_t is just an integer the algorithm
should be faster then linear search.


I'm not quite sure you are asking for but I'm going to assume that
lower_bound, upper_bound, and equal_range won't work.

Are you trying to find two instances of myclass who's associated time_t
object are within a certain range?

Maybe if you put the data in a multimap<myclass, time_t>, then
equal_range will give you all the myclass objects and you can compare
their time_ts... If I'm not even close, then you are going to have to
show some code. Give an example that works but is too slow and someone,
i'm sure, will be able to produce an example that is faster and still
does the same thing.
--
Magic depends on tradition and belief. It does not welcome observation,
nor does it profit by experiment. On the other hand, science is based
on experience; it is open to correction by observation and experiment.
Apr 9 '06 #2
> I'm not quite sure you are asking for but I'm going to assume that
lower_bound, upper_bound, and equal_range won't work.
Yes I'm sorry about beeing unclear. It's very easy to be quite unclear when
you do something quite technical and have been sitting with it for a while.

I think lower_bound might solve my problem though.

The basic idea is that I do statistics at specific intervals e.g. every 10
min. The gathered values are stored as 'second' for the specific time_t.
This way I can go through each record and see at what time it was gathered.

Here is the original (slow!) algorithm:

int CStatistics::GetMaxValueInPeriod(time_t tFrom, time_t tTo)

{

UseMap::iterator it;

int nMaxValue = 0;

for (it = m_pUseMap->begin();

it != m_pUseMap->end();

it++)

{

if (it->first < tFrom)

continue;

if (it->first > tTo)

break;

if (nMaxValue < it->second.m_nTotalFoo)

nMaxValue = it->second.m_m_nTotalFoo;

}

return nMaxValue;

}

Assume it contains values from since 2 years ago which is the worst case
scenario for me.

Then in order to find the first values which fits in my range I scan forward
by omitting all values which were earlier then the time I want.

This takes a lot of time even for a few values. Can lower_bound help me?
Are you trying to find two instances of myclass who's associated time_t
object are within a certain range?
No. I'm trying to find all instances of myclass which falls within a
specific timerange in order to perform caluculations on them. The algorithm
above is just one of many.
Maybe if you put the data in a multimap<myclass, time_t>, then
equal_range will give you all the myclass objects and you can compare
their time_ts... If I'm not even close, then you are going to have to
show some code. Give an example that works but is too slow and someone,
i'm sure, will be able to produce an example that is faster and still
does the same thing.


Perhaps multimap would work as well. I havn't spent enough time on multimap
structure to be able to tell. Theres always a complexity vs. speed limit.
I'd rather have easy to read code naturally so if possible I'll stick to
map.

Thanks in advance.
-- Henrik
Apr 9 '06 #3
In article <44***********************@dread15.news.tele.dk> ,
"Henrik Goldman" <he************@mail.tele.dk> wrote:
I'm not quite sure you are asking for but I'm going to assume that
lower_bound, upper_bound, and equal_range won't work.


Yes I'm sorry about beeing unclear. It's very easy to be quite unclear when
you do something quite technical and have been sitting with it for a while.

I think lower_bound might solve my problem though.

The basic idea is that I do statistics at specific intervals e.g. every 10
min. The gathered values are stored as 'second' for the specific time_t.
This way I can go through each record and see at what time it was gathered.

Here is the original (slow!) algorithm:

int CStatistics::GetMaxValueInPeriod(time_t tFrom, time_t tTo)

{

UseMap::iterator it;

int nMaxValue = 0;

for (it = m_pUseMap->begin();

it != m_pUseMap->end();

it++)

{

if (it->first < tFrom)

continue;

if (it->first > tTo)

break;

if (nMaxValue < it->second.m_nTotalFoo)

nMaxValue = it->second.m_m_nTotalFoo;

}

return nMaxValue;

}

Assume it contains values from since 2 years ago which is the worst case
scenario for me.

Then in order to find the first values which fits in my range I scan forward
by omitting all values which were earlier then the time I want.

This takes a lot of time even for a few values. Can lower_bound help me?


bool comp( const UseMap::value_type& lhs, const UseMap::value_type& rhs )
{
return lhs.second.m_m_nTotalFoo < rhs.second.m_m_nTotalFoo;
}

int CStatistics::GetMaxValueInPeriod( time_t tFrom, time_t tTo )
{
assert( tFrom <= tTo );
UseMap::iterator begin = m_pUseMap->lower_bound( tFrom );
UseMap::iterator end = m_pUseMap->upper_bound( tTo );
if ( begin == end )
throw runtime_error( "no such period" );
return max_element( begin, end, &comp )->second.m_m_nTotalFoo;
}

I think you will find something like the above much faster. Of course
I'm guessing as to some of the types because you didn't give compilable
code.

Depending on how many elements are in the map, and how big the range is:

int CStatistics::GetMaxValueInPeriod( time_t tFrom, time_t tTo )
{
assert( tFrom <= tTo );
UseMap::iterator begin = m_pUseMap->lower_bound( tFrom );
UseMap::iterator end = begin;
while ( end->first < tTo )
++end;
if ( begin == end )
throw runtime_error( "no such period" );
return max_element( begin, end, &comp )->second.m_m_nTotalFoo;
}

Might be faster, you'll have to measure the two and see which is better
for you.

Finally there is:

int CStatistics::GetMaxValueInPeriod( time_t tFrom, time_t tTo )
{
assert( tFrom <= tTo );
UseMap::iterator begin = m_pUseMap->lower_bound( tFrom );
if ( begin->first < tTo )
throw runtime_error( "no such period" );
int result = begin->second.m_m_nTotalFoo;
++begin;
while ( begin->first < tTo ) {
if ( begin->second.m_m_nTotalFoo > result )
result = begin->second.m_m_nTotalFoo;
++begin;
}
return result;
}

Which is a little harder to read, but may be a hair faster than the
second example.
--
Magic depends on tradition and belief. It does not welcome observation,
nor does it profit by experiment. On the other hand, science is based
on experience; it is open to correction by observation and experiment.
Apr 9 '06 #4

This thread has been closed and replies have been disabled. Please start a new discussion.

Similar topics

3
by: hivie | last post by:
I have a problem that is causing me problems. I have a text file that stores 5 lines of crap (stuff that I dont need( for the user only)). After that there is data that is in three columns...
4
by: James | last post by:
We have a need to search through an entire drive for a specific file name. The process is currently written with recursive loops through each directory and the Scripting.FileSystemObject. Problem...
2
by: Jim Kitterman | last post by:
I am looking for the most efficient way of searching a large xml document (> 14mg). If I could get some pointers in the right direction. I am using VB.NET. It is readonly.
2
by: SR | last post by:
Hi, I was wondering if there any good books or articles on efficient programming in C to achieve reductions in computation time(especially in parallel environments) etc. Pointers to any books or...
7
by: junky_fellow | last post by:
Can anyone suggest some efficient way to search a substring in a text file. For eg. suppose i want to search the pattern "abc" in a text file, then which algorithm should i use. I just want some...
2
by: Carlos K | last post by:
Hello I'm having some difficulty searching a set of rows in a DataRow collection.. This is my question What would be an efficient way to search any column of an DataRow array Let me try to...
22
by: Curious | last post by:
Hi, I am searching for a data structure that stores key-value pairs in it. This data structure is to hold large amounts of key-value pairs, and so needs to be efficient both in insertion and...
3
by: Manogna | last post by:
hi ! I have two big files like A anb B. A contains nearly 1000 lines. and B contains 1500000 lines.
0
by: taylorcarr | last post by:
A Canon printer is a smart device known for being advanced, efficient, and reliable. It is designed for home, office, and hybrid workspace use and can also be used for a variety of purposes. However,...
0
by: Charles Arthur | last post by:
How do i turn on java script on a villaon, callus and itel keypad mobile phone
0
by: aa123db | last post by:
Variable and constants Use var or let for variables and const fror constants. Var foo ='bar'; Let foo ='bar';const baz ='bar'; Functions function $name$ ($parameters$) { } ...
0
by: ryjfgjl | last post by:
In our work, we often receive Excel tables with data in the same format. If we want to analyze these data, it can be difficult to analyze them because the data is spread across multiple Excel files...
1
by: nemocccc | last post by:
hello, everyone, I want to develop a software for my android phone for daily needs, any suggestions?
0
marktang
by: marktang | last post by:
ONU (Optical Network Unit) is one of the key components for providing high-speed Internet services. Its primary function is to act as an endpoint device located at the user's premises. However,...
0
by: Hystou | last post by:
Most computers default to English, but sometimes we require a different language, especially when relocating. Forgot to request a specific language before your computer shipped? No problem! You can...
0
Oralloy
by: Oralloy | last post by:
Hello folks, I am unable to find appropriate documentation on the type promotion of bit-fields when using the generalised comparison operator "<=>". The problem is that using the GNU compilers,...
0
jinu1996
by: jinu1996 | last post by:
In today's digital age, having a compelling online presence is paramount for businesses aiming to thrive in a competitive landscape. At the heart of this digital strategy lies an intricately woven...

By using Bytes.com and it's services, you agree to our Privacy Policy and Terms of Use.

To disable or enable advertisements and analytics tracking please visit the manage ads & tracking page.