C++Talk.NET Forum Index C++Talk.NET
C++ language newsgroups
 
Archives   FAQFAQ   SearchSearch   MemberlistMemberlist   UsergroupsUsergroups   RegisterRegister 
 ProfileProfile   Log in to check your private messagesLog in to check your private messages   Log inLog in 

elements common to more than one vector...

 
Post new topic   Reply to topic    C++Talk.NET Forum Index -> C++ language (comp.lang.c++)
View previous topic :: View next topic  
Author Message
Winbatch
Guest





PostPosted: Fri Feb 24, 2006 11:06 pm    Post subject: elements common to more than one vector... Reply with quote



Is there a function that I can use that given a few vectors which elements
are common to all?

for example
vector<int> a;
vector<int> b;

a.push_back( 1 );
a.push_back( 2 );
a.push_back( 3 );
a.push_back( 4 );

b.push_back( 2 );
b.push_back( 4 );

Something that will give me back the answer of 2 and 4? (The results would
be stored in another vector).

What if I have more than 2 vectors to compare - would I somehow call this
function against each pair? (ie a vs. b, b vs. c, a vs. c?)
Back to top
Guest






PostPosted: Fri Feb 24, 2006 11:06 pm    Post subject: Re: elements common to more than one vector... Reply with quote



Winbatch wrote:
Quote:
Is there a function that I can use that given a few vectors which elements
are common to all?

for example
vector<int> a;
vector<int> b;

a.push_back( 1 );
a.push_back( 2 );
a.push_back( 3 );
a.push_back( 4 );

b.push_back( 2 );
b.push_back( 4 );

Something that will give me back the answer of 2 and 4? (The results would
be stored in another vector).

What if I have more than 2 vectors to compare - would I somehow call this
function against each pair? (ie a vs. b, b vs. c, a vs. c?)

Maybe you really want to be playing with std::set?
Back to top
Winbatch
Guest





PostPosted: Fri Feb 24, 2006 11:06 pm    Post subject: Re: elements common to more than one vector... Reply with quote



Quote:

Maybe you really want to be playing with std::set?


Even if I did switch to set, my question still stands, right?
Back to top
Winbatch
Guest





PostPosted: Fri Feb 24, 2006 11:06 pm    Post subject: Re: elements common to more than one vector... Reply with quote

"Winbatch" <winbatch (AT) techie (DOT) com> wrote in message
news:3%LLf.5566$uV6.175@news-wrt-01.rdc-nyc.rr.com...
Quote:

Maybe you really want to be playing with std::set?


Even if I did switch to set, my question still stands, right?


Is it with set_intersection? What if I have more than 2 sets? I guess I
just do the function call for each set against the last?
Back to top
Daniel T.
Guest





PostPosted: Sat Feb 25, 2006 12:06 am    Post subject: Re: elements common to more than one vector... Reply with quote

In article <eTLLf.5565$uV6.3165@news-wrt-01.rdc-nyc.rr.com>,
"Winbatch" <winbatch (AT) techie (DOT) com> wrote:

Quote:
Is there a function that I can use that given a few vectors which elements
are common to all?

for example
vector<int> a;
vector<int> b;

a.push_back( 1 );
a.push_back( 2 );
a.push_back( 3 );
a.push_back( 4 );

b.push_back( 2 );
b.push_back( 4 );

Something that will give me back the answer of 2 and 4? (The results would
be stored in another vector).

What if I have more than 2 vectors to compare - would I somehow call this
function against each pair? (ie a vs. b, b vs. c, a vs. c?)

There is no such function, but you can easily write one using
find_first_of as a basis.


template < typename InIt, typename ForIt, typename OutIt >
void copy_all_of( InIt first1, InIt last1, ForIt first2, ForIt last2,
OutIt first3 )
{
InIt it = find_first_of( first1, last1, first2, last2 );
while ( it != last1 ) {
*first3++ = *it++;
it = find_first_of( it, last1, first2, last2 );
}
}

template < typename InIt, typename ForIt, typename OutIt,
typename BinPred >
void copy_all_of( InIt first1, InIt last1, ForIt first2, ForIt last2,
OutIt first3, BinPred fn )
{
InIt it = find_first_of( first1, last1, first2, last2, fn );
while ( it != last1 ) {
*first3++ = *it++;
it = find_first_of( it, last1, first2, last2, fn );
}
}


--
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.
Back to top
Kai-Uwe Bux
Guest





PostPosted: Sat Feb 25, 2006 12:06 am    Post subject: Re: elements common to more than one vector... Reply with quote

Winbatch wrote:

Quote:
Is there a function that I can use that given a few vectors which elements
are common to all?

for example
vector<int> a;
vector<int> b;

a.push_back( 1 );
a.push_back( 2 );
a.push_back( 3 );
a.push_back( 4 );

b.push_back( 2 );
b.push_back( 4 );

Something that will give me back the answer of 2 and 4? (The results would
be stored in another vector).

What if I have more than 2 vectors to compare - would I somehow call this
function against each pair? (ie a vs. b, b vs. c, a vs. c?)

If you can afford to sort the vectors, you can use

std::set_intersection()

to form the intersection of two sorted sequences. Since the result is itself
a sorted sequence, you can iterate that procedure through all your vectors.
Something like:


#include <vector>
#include <algorithm>
#include <iterator>
#include <iostream>

template < typename T >
void cumulative_intersection ( std::vector<T> & current,
std::vector<T> const & next ) {
std::vector<T> dummy;
std::set_intersection( current.begin(), current.end(),
next.begin(), next.end(),
std::back_inserter( dummy ) );
std::swap( current, dummy );
}


typedef std::vector< int > IntVector;
int main ( void ) {
IntVector a;
a.push_back( 0 );
a.push_back( 1 );
a.push_back( 3 );
a.push_back( 4 );
IntVector b;
b.push_back( 0 );
b.push_back( 3 );
b.push_back( 4 );
b.push_back( 5 );
IntVector c;
c.push_back( 1 );
c.push_back( 4 );
c.push_back( 5 );

IntVector i = a;
cumulative_intersection( i, b );
cumulative_intersection( i, c );
std::copy( i.begin(), i.end(),
std::ostream_iterator< int >( std::cout, "\n" ) );
}


Best

Kai-Uwe Bux
Back to top
Winbatch
Guest





PostPosted: Sat Feb 25, 2006 12:06 am    Post subject: Re: elements common to more than one vector... Reply with quote

"Kai-Uwe Bux" <jkherciueh (AT) gmx (DOT) net> wrote in message
news:dto3h8$ao4$1 (AT) murdoch (DOT) acc.Virginia.EDU...
Quote:
Winbatch wrote:

Is there a function that I can use that given a few vectors which
elements
are common to all?

for example
vector<int> a;
vector<int> b;

a.push_back( 1 );
a.push_back( 2 );
a.push_back( 3 );
a.push_back( 4 );

b.push_back( 2 );
b.push_back( 4 );

Something that will give me back the answer of 2 and 4? (The results
would
be stored in another vector).

What if I have more than 2 vectors to compare - would I somehow call this
function against each pair? (ie a vs. b, b vs. c, a vs. c?)

If you can afford to sort the vectors, you can use

std::set_intersection()

to form the intersection of two sorted sequences. Since the result is
itself
a sorted sequence, you can iterate that procedure through all your
vectors.
Something like:


#include <vector
#include <algorithm
#include <iterator
#include <iostream

template < typename T
void cumulative_intersection ( std::vector<T> & current,
std::vector<T> const & next ) {
std::vector<T> dummy;
std::set_intersection( current.begin(), current.end(),
next.begin(), next.end(),
std::back_inserter( dummy ) );
std::swap( current, dummy );
}


typedef std::vector< int > IntVector;
int main ( void ) {
IntVector a;
a.push_back( 0 );
a.push_back( 1 );
a.push_back( 3 );
a.push_back( 4 );
IntVector b;
b.push_back( 0 );
b.push_back( 3 );
b.push_back( 4 );
b.push_back( 5 );
IntVector c;
c.push_back( 1 );
c.push_back( 4 );
c.push_back( 5 );

IntVector i = a;
cumulative_intersection( i, b );
cumulative_intersection( i, c );
std::copy( i.begin(), i.end(),
std::ostream_iterator< int >( std::cout, "\n" ) );
}


Best

Kai-Uwe Bux

Kai, it doesn't seem to work right. If I add c.push_back( 3 ) to your
example, I still only get output of '4'.
Back to top
Kai-Uwe Bux
Guest





PostPosted: Sat Feb 25, 2006 12:06 am    Post subject: Re: elements common to more than one vector... Reply with quote

Winbatch wrote:

Quote:

Kai

It's Kai-Uwe.


Quote:
, it doesn't seem to work right. If I add c.push_back( 3 ) to your
example, I still only get output of '4'.



I take that back - it works if I insert them in order . I guess I would
have to run sort () against each one before running the intersection...

Yup: set_intersection() operates on sorted input sequences.


Best

Kai-Uwe Bux
Back to top
Winbatch
Guest





PostPosted: Sat Feb 25, 2006 12:06 am    Post subject: Re: elements common to more than one vector... Reply with quote

Quote:
Kai, it doesn't seem to work right. If I add c.push_back( 3 ) to your
example, I still only get output of '4'.



I take that back - it works if I insert them in order . I guess I would

have to run sort () against each one before running the intersection...
Back to top
Neil Cerutti
Guest





PostPosted: Mon Feb 27, 2006 5:06 pm    Post subject: Re: elements common to more than one vector... Reply with quote

On 2006-02-24, Daniel T. <postmaster (AT) earthlink (DOT) net> wrote:
Quote:
In article <eTLLf.5565$uV6.3165@news-wrt-01.rdc-nyc.rr.com>,
"Winbatch" <winbatch (AT) techie (DOT) com> wrote:

Is there a function that I can use that given a few vectors which elements
are common to all?

for example
vector<int> a;
vector<int> b;

a.push_back( 1 );
a.push_back( 2 );
a.push_back( 3 );
a.push_back( 4 );

b.push_back( 2 );
b.push_back( 4 );

Something that will give me back the answer of 2 and 4? (The
results would be stored in another vector).

What if I have more than 2 vectors to compare - would I somehow
call this function against each pair? (ie a vs. b, b vs. c, a
vs. c?)

There is no such function, but you can easily write one using
find_first_of as a basis.

You thought that was easy? ;-)

Quote:
template < typename InIt, typename ForIt, typename OutIt

find_first_of requires InIt and ForIt both to be Forward Iterator
types. It looks like you're implying that first1 and first2 could be
input iterators, when they cannot.

Quote:
void copy_all_of( InIt first1, InIt last1, ForIt first2, ForIt last2,
OutIt first3 )

Convention is to return a copy of the output iterator. The practice
might even be useful for error checking.

Quote:
{
InIt it = find_first_of( first1, last1, first2, last2 );
while ( it != last1 ) {
*first3++ = *it++;
it = find_first_of( it, last1, first2, last2 );
}
}

Pretty cool.

--
Neil Cerutti
We really didn't deserve to win. They didn't either. It should
have been a tie. --Sam Cassell
Back to top
Daniel T.
Guest





PostPosted: Mon Feb 27, 2006 8:06 pm    Post subject: Re: elements common to more than one vector... Reply with quote

In article <slrne06blt.1lo.leadvoice (AT) FIAD06 (DOT) norwich.edu>,
Neil Cerutti <leadvoice (AT) email (DOT) com> wrote:

Quote:
On 2006-02-24, Daniel T. <postmaster (AT) earthlink (DOT) net> wrote:
In article <eTLLf.5565$uV6.3165@news-wrt-01.rdc-nyc.rr.com>,
"Winbatch" <winbatch (AT) techie (DOT) com> wrote:

Is there a function that I can use that given a few vectors which elements
are common to all?

for example
vector<int> a;
vector<int> b;

a.push_back( 1 );
a.push_back( 2 );
a.push_back( 3 );
a.push_back( 4 );

b.push_back( 2 );
b.push_back( 4 );

Something that will give me back the answer of 2 and 4? (The
results would be stored in another vector).

What if I have more than 2 vectors to compare - would I somehow
call this function against each pair? (ie a vs. b, b vs. c, a
vs. c?)

There is no such function, but you can easily write one using
find_first_of as a basis.

You thought that was easy? Wink

Well yea, I thought it was a pretty standard idiom for using find
functions... Find the first instance then loop through finding others
until done.


Quote:
template < typename InIt, typename ForIt, typename OutIt

find_first_of requires InIt and ForIt both to be Forward Iterator
types. It looks like you're implying that first1 and first2 could be
input iterators, when they cannot.

Maybe I'm missing something... According to sgi's website, the first
range can be input iterators...
<http://www.sgi.com/tech/stl/find_first_of.html>


Quote:
void copy_all_of( InIt first1, InIt last1, ForIt first2, ForIt last2,
OutIt first3 )

Convention is to return a copy of the output iterator. The practice
might even be useful for error checking.

Agreed.

Quote:
{
InIt it = find_first_of( first1, last1, first2, last2 );
while ( it != last1 ) {
*first3++ = *it++;
it = find_first_of( it, last1, first2, last2 );
}
return first3;
}




--
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.
Back to top
Neil Cerutti
Guest





PostPosted: Wed Mar 01, 2006 4:06 pm    Post subject: Re: elements common to more than one vector... Reply with quote

On 2006-02-27, Daniel T. <postmaster (AT) earthlink (DOT) net> wrote:
Quote:
In article <slrne06blt.1lo.leadvoice (AT) FIAD06 (DOT) norwich.edu>,
Neil Cerutti <leadvoice (AT) email (DOT) com> wrote:
find_first_of requires InIt and ForIt both to be Forward Iterator
types. It looks like you're implying that first1 and first2 could be
input iterators, when they cannot.

Maybe I'm missing something... According to sgi's website, the first
range can be input iterators...
http://www.sgi.com/tech/stl/find_first_of.html

I used my own copy of library documentation (Rogue Wave). Perhaps this
requirement has changed? The draft copy of the C++98 standard says
ForwardIterators are required for find_first_of, but I can't think why
that *should* be a requirement. The obvious implementation of
find_first_of doesn't need to do more than one pass through, does it?

--
Neil Cerutti
Back to top
Daniel T.
Guest





PostPosted: Thu Mar 02, 2006 1:06 pm    Post subject: Re: elements common to more than one vector... Reply with quote

In article <slrne0becs.1qg.leadvoice (AT) FIAD06 (DOT) norwich.edu>,
Neil Cerutti <leadvoice (AT) email (DOT) com> wrote:

Quote:
On 2006-02-27, Daniel T. <postmaster (AT) earthlink (DOT) net> wrote:
In article <slrne06blt.1lo.leadvoice (AT) FIAD06 (DOT) norwich.edu>,
Neil Cerutti <leadvoice (AT) email (DOT) com> wrote:
find_first_of requires InIt and ForIt both to be Forward Iterator
types. It looks like you're implying that first1 and first2 could be
input iterators, when they cannot.

Maybe I'm missing something... According to sgi's website, the first
range can be input iterators...
http://www.sgi.com/tech/stl/find_first_of.html

I used my own copy of library documentation (Rogue Wave). Perhaps this
requirement has changed? The draft copy of the C++98 standard says
ForwardIterators are required for find_first_of, but I can't think why
that *should* be a requirement. The obvious implementation of
find_first_of doesn't need to do more than one pass through, does it?

No it doesn't. However I see that Stroustrup also shows the forward
iterator requirement, and after playing around with it for a bit, I
can't think of anything useful you could do with the return value if it
is a forward iterator, about the only think you can do is compare it to
end to see if the value_type exists in the stream.

int main() {
const char vowels[] = { "aeiouAEIOU" };
if ( find_first_of( istream_iterator<char>(cin),
istream_iterator<char>(), vowels, vowels + 10 ) !=
istream_iterator<char>() )
cout << "a vowel was typeped.\n";
else
cout << "no vowels found\n";
}



--
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.
Back to top
Neil Cerutti
Guest





PostPosted: Thu Mar 02, 2006 3:06 pm    Post subject: Re: elements common to more than one vector... Reply with quote

On 2006-03-02, Daniel T. <postmaster (AT) earthlink (DOT) net> wrote:
Quote:
In article <slrne0becs.1qg.leadvoice (AT) FIAD06 (DOT) norwich.edu>,
Neil Cerutti <leadvoice (AT) email (DOT) com> wrote:
I used my own copy of library documentation (Rogue Wave). Perhaps
this requirement has changed? The draft copy of the C++98 standard
says ForwardIterators are required for find_first_of, but I can't
think why that *should* be a requirement. The obvious
implementation of find_first_of doesn't need to do more than one
pass through, does it?

No it doesn't. However I see that Stroustrup also shows the forward
iterator requirement, and after playing around with it for a bit, I
can't think of anything useful you could do with the return value if
it is a forward iterator, about the only think you can do is compare
it to end to see if the value_type exists in the stream.

I assume you meant to say input iterator the last time.

Quote:
int main() {
const char vowels[] = { "aeiouAEIOU" };
if ( find_first_of( istream_iterator<char>(cin),
istream_iterator<char>(), vowels, vowels + 10 ) !=
istream_iterator<char>() )
cout << "a vowel was typeped.\n";
else
cout << "no vowels found\n";
}

That's interesting. It occurred to me that might be the rationale.
But it doesn't seem like a good one for prohibiting input iterators.
The standard provides the analogous binary_search, after all. Finding
out if one of a set of characters was in the input stream seems
equally useful to binary_search.

--
Neil Cerutti
Not only is he ambidextrous, he can throw with either hand.
--Duff Daugherty
Back to top
Display posts from previous:   
Post new topic   Reply to topic    C++Talk.NET Forum Index -> C++ language (comp.lang.c++) All times are GMT
Page 1 of 1

 
Jump to:  
You cannot post new topics in this forum
You cannot reply to topics in this forum
You cannot edit your posts in this forum
You cannot delete your posts in this forum
You cannot vote in polls in this forum


Powered by phpBB © 2001, 2006 phpBB Group
SEO toolkit © 2004-2006 webmedic.