vijayan121 1,152 Posting Virtuoso

If the intent was to use std::copy and stream iterators, I have nothing to add.

If the intent was to write a function to copy a file, this would be easier and also more efficient.

bool copy_file( const char* input_file, const char* output_file )
{ return std::ofstream( output_file ) <<  std::ifstream(input_file).rdbuf() ; }
vijayan121 1,152 Posting Virtuoso

> my compilers::tdm gcc4.5.2

You have a current C++ compiler; prefer using std::bind over boost::bind (compile with -std=c++0x)

> I don't know how to solve the overloaded problem like this one

boost::bind or std::bind have no good way to figure out which overload you intended to bind. You have to disambiguate the overload yourself. For example:

#include <iostream>
#include <boost/bind.hpp>
#include <boost/function.hpp>
#include <functional>

int foobar( int a, int b ) { return a+b ; }

double foobar( double a, double& b, double c ) { return b = a-b+c ; }

int main()was meant to be bound.
{
    // disabiguate the overloaded functions for boost::bind
    int (&int_foobar)(int,int) = foobar ;
    double (&dbl_foobar)(double,double&,double) = foobar ;

    boost::function< int(int) > f1 = boost::bind( int_foobar, _1, 23 ) ;
    std::cout << f1(99) << '\n' ;

    double b = 56.2 ;
    boost::function< double(double,double) > f2 = 
                                    boost::bind( dbl_foobar, _1, boost::ref(b), _2 ) ;
    std::cout << f2( 17.4, 23.9 ) << ' ' << b << '\n' ;

    // same disambiguation is also needed for C++0x std::bind
    std::function< int(int) > f3 = std::bind( int_foobar, std::placeholders::_1, 23 ) ;
    std::cout << f3(99) << '\n' ;

    b = 56.2 ;
    // but in C++0x using a lambda function instead is so much easier
    auto f4 = [&b] ( double a, double c ) { return foobar(a,b,c) ; } ;
    std::cout << f4( 17.4, 23.9 ) << ' ' << b <<  '\n' ;
}
vijayan121 1,152 Posting Virtuoso

The second argument to RegisterHotKey() is the id of the hot key. If multiple WM_HOTKEY messages are received by the same thread, you need to examine the lParam of the message for the id of the hot key that was pressed.

enum { F9_KEYID = 1, F10_KEYID = 2 } ;
RegisterHotKey( 0, F9_KEYID, MOD_NOREPEAT, VK_F9 ) ;
RegisterHotKey( 0, F10_KEYID, MOD_NOREPEAT, VK_F10 ) ;

MSG msg ;
while( GetMessage( &msg, 0, 0, 0) )
{
    if(msg.message == WM_HOTKEY)
    {
        switch( HIWORD(msg.lParam) )
        {
            case F9_KEYID : MessageBox::Show("F9 was pressed") ; break ;
            case F10_KEYID : MessageBox::Show("F10 was pressed") ; break ;
            default: MessageBox::Show("some other hot key was pressed") ;
        }
    }
    // ...
}

Tip: avoid using magic numbers in your code.

triumphost commented: U ARE AMAZING! +2
vijayan121 1,152 Posting Virtuoso

> The more I study about programming, I finf out that to become a competent programmer
> I have to know many things, and looks like I would never end up learning

Yes. It is a journey that never ends.

vijayan121 1,152 Posting Virtuoso

Declaration

void Resultant(const double[], const double[], const double[], [B]const[/B] double[], const int, double&, double&, double&);

does not match the definition

void Resultant(const double M[], const double X[], const double Y[], [B]/* ??? */[/B] double Z[], const int moves, double& Rx, double& Ry, double& Rz)
{
   // ...

Not a great idea, writing a function with eight(!) parameters.

vijayan121 1,152 Posting Virtuoso
vijayan121 1,152 Posting Virtuoso
int main()
{
    int a, b;
    char c ;

    // ...

    ins >> a >> c >> b;    
    cout <<a <<b;
}
vijayan121 1,152 Posting Virtuoso

There are many different ways to do this. Perhaps, the simplest is this:

#include <fstream>
#include <set>
#include <string>
#include <iterator>
#include <algorithm>
#include <iostream>

template< typename T > std::set<T> file_to_set( const char* path )
{
    std::ifstream file(path) ;
    return std::set<T>( std::istream_iterator<T>(file), std::istream_iterator<T>() ) ;
}

int main()
{
    const std::set< std::string> a = file_to_set< std::string >( "a.txt" ) ;
    const std::set< std::string> b = file_to_set< std::string >( "b.txt" ) ;
    std::set_difference( a.begin(), a.end(), b.begin(), b.end(),
                         std::ostream_iterator< std::string >( std::cout, "\n" ) ) ;
}
vijayan121 1,152 Posting Virtuoso

> what should I know before I try to extend it?
> Should I know some metaprogramming language or the other's part of the boost?

You need to read up on the accumulator framework and concepts.
You also need to have a basic knowledge of the Boost.Parameter library.
For anything not very trivial, it would help if you understand Boost.MPL Lambda Expressions and Boost.MPL Metafunctions/Metafunction Classes.

The basics are straight forward as illustrated here: http://www.boost.org/doc/libs/1_46_0/doc/html/accumulators/user_s_guide.html#accumulators.user_s_guide.the_accumulators_framework.extending_the_accumulators_framework.defining_a_new_accumulator

1. Define your new accumulator (ideally in boost::accumulators::impl). It must derive from accumulator_base
2. In boost::accumulators::tag, define a tag for it. Your tag must inherit from depends_on<>.
3. In boost::accumulators::extract define an extractor for it. And hoist the extractor to the boost::accumulators namespace.


Here is a trivial example that accumulates the average of the last decimal digit of (integral) sample values:

#include <boost/accumulators/accumulators.hpp>
#include <boost/accumulators/statistics/stats.hpp>
#include <boost/accumulators/statistics/mean.hpp>
#include <boost/accumulators/framework/parameters/sample.hpp>
#include <boost/type_traits.hpp>
#include <boost/mpl/assert.hpp>
#include <iostream>

namespace boost
{
    namespace accumulators
    {
        namespace impl
        {
            template< typename T > struct average_last_digit : accumulator_base
            {
                BOOST_MPL_ASSERT( ( is_integral<T> ) ) ;

                typedef typename boost::common_type< T, double >::type result_type ;

                template< typename ARGS >  average_last_digit( const ARGS& args )
                  : sum_of_last_digits( args[ sample | T() ] ) {}

                template< typename ARGS > void operator () ( const ARGS& args )
                { sum_of_last_digits += args[sample] % 10 ; 

                template< typename ARGS > result_type result( const ARGS& args ) const
                { return sum_of_last_digits / count( args[accumulator] …
vijayan121 1,152 Posting Virtuoso

You could also use a stringstream to do the conversion.

typedef unsigned char byte ;

std::vector<byte> to_byte_sequence( const std::string& str )
{
    std::vector<byte> result ;

    std::istringstream stm(str) ;
    stm >> std::hex >> std::noshowbase ;

    unsigned int b ;
    while( stm >> b ) result.push_back(b) ;

    if( stm.eof() ) return result ;
    else throw std::invalid_argument( "badly formed string" ) ;
}
vijayan121 1,152 Posting Virtuoso

> Because not every statistical data could be computed without saving the input values

Boost.Accumulators is a library for incremental statistical computation.

Incremental computation means that the statistic is updated each time new data arrives. Incremental computation of statistics use algorithms that are quite different from static computation algorithms.

For an example, see: http://www.johndcook.com/standard_deviation.html

For incremental computation of statistics like median, which would otherwise require the entire data set, estimators are used. http://www.boost.org/doc/libs/1_46_1/doc/html/accumulators/user_s_guide.html#accumulators.user_s_guide.the_statistical_accumulators_library.median

vijayan121 1,152 Posting Virtuoso
class UpperCaseMonitor : [B]public[/B] Observable
{
  // ...
vijayan121 1,152 Posting Virtuoso

I've found that often in my code I have a need for primitive variables protected with synchronization objects such as a boost::mutex

If by primitive variables you mean variables of types like int, double, pointer and so on, using heavy weight synchronization (using mutexes and so on) as a general purpose technique is ill-advised (performance).

If you have a compiler that supports C++0x atomics, use that. The <atomic> header is closely coupled to the innards of the compiler; and ideally results in highly optimized machine code being generated. Something that is not otherwise representable by higher level C or C++ constructs. See N3092 for details http://www.open-std.org/JTC1/SC22/WG21/docs/papers/2010/n3092.pdf

For example,

#include <iostream>
#include <string>
#include <atomic>

int main()
{
    std::atomic<int> cnt(0) ; // specialization for int
    std::cout << ++cnt << '\n' ; // atomic increment
    std::cout << ( cnt += 6 ) << '\n' ;
    // etc

    std::string str[10] { "", "", "", "", "", "hello ", "", "", "", "" };
    std::atomic< std::string* > pointer( str ) ; // atomic pointer
    pointer += 2 ; // atomic increment
    pointer[3] += "world" ; // note: only the pointer operation is atomic here
    std::cout << pointer[3] << '\n' ;
}

If not you could use Boost.Atomic (not part of Boost release) if you are on a platform that it supports. http://www.chaoticmind.net/~hcb/projects/boost.atomic/

Other options include just::thread http://www.stdthread.co.uk/doc/headers/atomic.html, Intel TBB http://threadingbuildingblocks.org/

vijayan121 1,152 Posting Virtuoso

If the number of elements is large and the size of each element is small (eg. an array of int), the well known reverse three times technique seems to be the most efficient.

void reverse( int a[], std::size_t N )
{
    for( std::size_t i = 0 ; i < N/2 ; ++i ) std::swap( a[i], a[N-i-1] ) ;
}

void rotate_left( int a[], std::size_t N, int BY )
{
    BY %= N ;
    reverse( a, BY ) ;
    reverse( a+BY, N-BY ) ;
    reverse( a, N ) ;
}

Otherwise, something similar to a typical std::rotate() implementation.
http://cplusplus.com/reference/algorithm/rotate/

vijayan121 1,152 Posting Virtuoso

> Is accumulator_set using dynamic memory?

It shouldn't matter either way, should it?

vijayan121 1,152 Posting Virtuoso

> oops,the answer is 3.5 again, but the answer I want is 13.5

The simplest way would be to use a new accumulator_set<> for the fresh calculations.

If you want to reuse the same accumulator_set<> from scratch, just reinitialize it.

#include <iostream>
#include <new>
#include <boost/utility.hpp>
#include <boost/accumulators/accumulators.hpp>
#include <boost/accumulators/statistics/stats.hpp>
#include <boost/accumulators/statistics/mean.hpp>

template< typename DEFAULT_INITIALIZABLE >
inline void clear( DEFAULT_INITIALIZABLE& object )
{
    object.DEFAULT_INITIALIZABLE::~DEFAULT_INITIALIZABLE() ;
    ::new ( boost::addressof(object) ) DEFAULT_INITIALIZABLE() ;
}

int main()
{
    using namespace boost::accumulators ;

    accumulator_set< double, features< tag::count, tag::sum, tag::mean > > ac ;
    ac(123) ; ac(456) ; ac(789) ; ac(1234) ;
    std::cout << sum(ac) << '/' << count(ac) << " == " << mean(ac) << '\n' ;

    clear(ac) ;
    ac(1) ; ac(22) ; ac(333) ;
    std::cout << sum(ac) << '/' << count(ac) << " == " << mean(ac) << '\n' ;
}
vijayan121 1,152 Posting Virtuoso
vijayan121 1,152 Posting Virtuoso
vijayan121 1,152 Posting Virtuoso

A simple, reasonably fast algorithm to find the smallest prime factor of a number N would be:

a. generate all prime numbers up to the square root of N using a sieve algorithm.

b. the first (smallest) generated prime number that divides N is the smallest prime factor.

For example:

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

// sieve of sundaram (naive implementation)
std::vector<int> primes_upto( int N )
{
    const int M = N / 2 ;
    std::vector<bool> sieve( M, true ) ;
    for( int i = 1 ; i < M ; ++i )
    {
        const int L = (M-i) / ( 2*i + 1 ) ;
        for( int j = i ; j <= L ; ++j )
            sieve[ i + j + 2*i*j ] = false ;
    }

    std::vector<int> primes ;
    primes.push_back(2) ;
    for( int i = 1 ; i < M ; ++i )
        if( sieve[i] ) primes.push_back( i*2 + 1 ) ;
    return primes ;
}

int smallest_prime_factor( int N )
{
    if( N < 2 ) return N ;
    
    std::vector<int> primes = primes_upto( std::sqrt(N) + 1 ) ;
    for( std::vector<int>::size_type i = 0 ; i < primes.size() ; ++i )
        if( ( N % primes[i] ) == 0 ) return primes[i] ;
        
    return N ;
}

For large numbers (up to about 2^70 or so), the Brent-Pollard Rho algorithm is said to be the fastest.
http://en.wikipedia.org/wiki/Pollard%27s_rho_algorithm#Variants
http://www.remcobloemen.nl/2009/12/brent-pollard-%CF%81-factorisation/

vijayan121 1,152 Posting Virtuoso

If the number of vectors which have elements on which you want to perform a particular operation (for example, print it) is fixed, you could write a simple wrapper function:

#include <algorithm>

template< typename SEQ1, typename SEQ2, typename SEQ3, typename FUNCTION >
inline void for_each( SEQ1& seq1, SEQ2& seq2, SEQ3& seq3, FUNCTION do_it )
{
    std::for_each( seq1.begin(), seq1.end(), do_it ) ;
    std::for_each( seq2.begin(), seq2.end(), do_it ) ;
    std::for_each( seq3.begin(), seq3.end(), do_it ) ;
}

If not, you could overload the function for two, three, four ... sequences.

Or if you are using a compiler with support for C++0x variadic templates (like g++ 4.5 or 4.6 with -std=c++0X):

#include <algorithm>

template< typename FUNCTION, typename SEQUENCE >
inline void apply( FUNCTION do_it, SEQUENCE& seq )
{  std::for_each( seq.begin(), seq.end(), do_it ) ; }

template< typename FUNCTION, typename FIRST_SEQ, typename ...OTHER_SEQS >
inline void apply( FUNCTION do_it, FIRST_SEQ& first, OTHER_SEQS ... rest )
{  apply( do_it, first ) ; apply( do_it, rest ... ) ; }

#include <vector>
#include <list>
#include <iostream>
#include <iomanip>

int main()
{
    std::vector<int> vec1 = { 0, 1, 2, 3, 4, 5 } ;
    std::vector<int> vec2 = { 9, 8, 7, 6, 4, 5 } ;
    std::vector<int> lst3( vec1.size(), 77 ) ;
    std::vector<int> lst4( vec1.rbegin(), vec1.rend() ) ;

    const int LINESZ = vec1.size() ;
    int cnt = 0 ;
    auto print_it = [ & cnt, LINESZ ] ( int value )
    {
        ++cnt ;
        std::cout << std::setw(3) << value << ( cnt%LINESZ == 0 ? …
vijayan121 1,152 Posting Virtuoso

Generalized Kadane's algorithm (any input sequence containing values belonging to a numeric type):

#include <iterator>
#include <iostream>
#include <limits>
#include <algorithm>
#include <list>

template< typename INPUT_ITERATOR >
void print_max_sum_subsequence( INPUT_ITERATOR begin, INPUT_ITERATOR end,
                                 std::ostream& stm = std::cout )
{
    typedef typename std::iterator_traits<INPUT_ITERATOR>::value_type numeric_type ;
    stm << "\nsequence: [ " ;
    std::for_each( begin, end,
                   [&stm] ( const numeric_type& v ) { stm << v << ' ' ; } ) ;
    stm << "]\n" ;

    numeric_type max_sum = std::numeric_limits<numeric_type>::min() ;
    INPUT_ITERATOR max_subseq_first = begin ;
    INPUT_ITERATOR max_subseq_last = begin ;
    const numeric_type ZERO = numeric_type() ;

    numeric_type curr_max_sum = ZERO ;
    INPUT_ITERATOR curr_subseq_first = begin ;
    for( INPUT_ITERATOR curr_subseq_last = begin ; curr_subseq_last != end ; ++curr_subseq_last )
    {
         curr_max_sum += *curr_subseq_last ;

         if( curr_max_sum > max_sum )
         {
             max_sum = curr_max_sum ;
             max_subseq_first = curr_subseq_first ;
             max_subseq_last = curr_subseq_last ;
         }

         if( curr_max_sum < ZERO )
         {
             curr_max_sum = ZERO ;
             curr_subseq_first = curr_subseq_last ;
             ++curr_subseq_first ;
         }
    }

    stm << "a maximum sum subsequence: [ " ;
    if( max_sum >= ZERO )
    {
        ++max_subseq_last ;
        std::for_each( max_subseq_first, max_subseq_last,
                       [&stm] ( const numeric_type& v ) { stm << v << ' ' ; } ) ;
        stm << "] (sum:" << max_sum << ")\n" ;
    }
    else stm << "] (the empty sequence)\n" ;
}

// print_max_sum_subsequence() is used like this:

template< typename T, std::size_t N > inline std::size_t size( T(&)[N] ) { return N ; }

int main()
{
    const int a[] = { -9, 88, -17, -40, …
vijayan121 1,152 Posting Virtuoso

This is not Kadane's algorithm, is it? This algorithm makes multiple passes through the sequence including nested passes:

#include <limits>
#include <utility>

for (int j1=0;j1<=arraysize; j1++) // O(N)
{
     partial_sum(param2+j1,param2+arraysize,newSeq1+determine_start1); // O(N)

     for (int cycle_thru=0;cycle_thru<= length( newSeq1 ) ;cycle_thru++) // O( N*N)
     {
       // ...
     }
     
     // ...
}

Incidentally, this is not C++: int newSeq[summation(arraysize)]; The algorithm also used extra memory O(N*N); summation(N) yields N * (N+1) / 2.

Overall, it executes in cubic ( O(N*N*N) ) time and quadratic ( O(N*N) ) space.

Kadane's algorithm makes a single pass through the sequence, computing a running total of the maximum subsequence sum ending at that position. It executes in linear ( O(N) ) time and uses constant ( O(1) ) space.

Kadane's algorithm for an array of int:

// returns a pair of positions (the start and the end of the maximum sum subsequence) in array a
std::pair<std::size_t,std::size_t> find_max_sum_subsequence( const int a[], std::size_t N )
{
    int max_sum = std::numeric_limits<int>::min() ;
    std::size_t max_subseq_start_pos = 0 ;
    std::size_t max_subseq_end_pos = 0 ;

    int curr_max_sum = 0 ;
    std::size_t curr_subseq_start_pos = 0 ;
    std::size_t curr_subseq_end_pos = 0 ;
    for( ; curr_subseq_end_pos < N ; ++curr_subseq_end_pos )
    {
         curr_max_sum += a[curr_subseq_end_pos] ;

         if( curr_max_sum > max_sum )
         {
             max_sum = curr_max_sum ;
             max_subseq_start_pos = curr_subseq_start_pos ;
             max_subseq_end_pos = curr_subseq_end_pos ;
         }

         if( curr_max_sum < 0 )
         {
             curr_max_sum = 0 ;
             curr_subseq_start_pos = curr_subseq_end_pos + 1 ;
         }
    }
    return std::make_pair( max_subseq_start_pos, max_subseq_end_pos ) ;
}
vijayan121 1,152 Posting Virtuoso

Use a discriminated union.

struct int_or_char
{
    int_or_char( int ii = 0 ) : type(INT), i(ii) {}
    int_or_char( char cc ) : type(CHAR), c(cc) {}
    
    enum type_t { INT, CHAR } ;
    type_t type ;
    
    union
    {
        int i ;
        char c ;
    };

    // etc.
};

and now: Stack< int_or_char > stk ; stk.push(100) ; stk.push( 'a' ) ; etc.

vijayan121 1,152 Posting Virtuoso

The general rule is that a file in a directory named 'temp' or 'tmp' is a temporary file; one that is required only for the duration of the execution of the program that uses it. By convention, these can be safely deleted; no reasonable program is expected to break if a temporary file is removed.

vijayan121 1,152 Posting Virtuoso

The algorithm requires a large pool compared with the sample, else it can
happen that some sample[] element is never populated.
It is only guaranteed that the first element is not null, or do I miss something?

The reservoir algorithm (for simple random sampling without replacement of K lines in a file) works like this:

The reservoir size is fixed at K (the sample size).

A.
First (lines 27-31) create a reservoir of size K filled with the first K lines in the file.

while( sample.size() < K )
    {
        if( getline( stm, line ) ) sample.push_back(line) ;
        else throw range_error( "sample size too large" ) ;
    }

B.
Now read line K+1.
Generate a random integer uniformly distributed in the inclusive interval [0,K]
With probability K/(K+1), replace a random line in the reservoir with line K+1

size_t r = uniform_int_distribution<size_t>( 0, i )(engine) ;
        if( r < K ) sample[r] = line ;

So far, we have read K+1 lines of which K are in the reservoir.
Probability that line K+1 is in the reservoir is now K/(K+1).
Probability that line K+1 is not in the reservoir is 1/(K+1).

Probability that a particular line (say line 1) is now not in the reservoir is:
the probability that line K+1 replaced a line in the reservoir: K/(K+1)
multiplied by the probability that line 1 was the one that was replaced: 1/K (equal probability for any …

vijayan121 1,152 Posting Virtuoso

My problem is, how to prevent reading so many lines from the file, especially if I have to return more than one line. If I have to return k lines, the complexity is theta(k n^2). I would rather prefer theta(k n log n) .

To select K lines from a population containing an unknown number of lines, you do not have to repeat the selection of one random line many times. A reservoir sampling algorithm can do this in one pass. (The earlier example of selecting one random line is a special case of reservoir sampling; where the reservoir size is just one.)

#include <iostream>
#include <fstream>
#include <string>
#include <algorithm>
#include <iterator>
#include <vector>
#include <random>
#include <stdexcept>

using namespace std ;

// simple(st) reservoir algorithm for random sampling without replacement
//
// algorithm R (credited to Alan Waterman) from:
//    Random Sampling with a Reservoir' by Jeffry Scott Vitter,
//         ACM Transactions on Mathematical Software, March 1985
//    http://www.ittc.ku.edu/~jsv/Papers/Vit85.Reservoir.pdf
//
// randomly select K (different) lines from an input stream opened in text mode
// time complexity is O(N)
template< typename RNG >
vector<string> random_lines( istream& stm, size_t K, RNG& engine )
{
    vector<string> sample ;
    std::string line ;

    while( sample.size() < K )
    {
        if( getline( stm, line ) ) sample.push_back(line) ;
        else throw range_error( "sample size too large" ) ;
    }

    for( size_t i = K ; getline( stm, line ) ; ++i )
    {
        size_t r = uniform_int_distribution<size_t>( 0, i )(engine) ; …
vijayan121 1,152 Posting Virtuoso

I have a global map (probably a bad idea) and I want to explicitly free it's used memory
The functions clear() only removes all elements, it doesn't free any memory.

Something like this, perhaps:

template < typename KEY, typename DATA, typename CMP_KEYS = std::less<KEY>,
            typename ALLOCATOR = std::allocator< std::pair<const KEY,DATA> > >
struct lean_map : public std::map< KEY, DATA, CMP_KEYS, ALLOCATOR >
{
    void clear() { lean_map::~lean_map() ; new (this) lean_map ; }
};

lean_map< int, int > my_map ;

int main()
{
    // use my_map
    my_map[123] = 456789 ;
    // etc

    my_map.clear() ;
}

The same idea, generalised (for any type with default initialisation):

template < typename T > struct scoped_use : boost::noncopyable
{
    explicit scoped_use( T& obj ) : object(obj) {}
    ~scoped_use()
    {
        void* here = boost::addressof(object) ;
        object.T::~T() ;
        new (here) T() ;
    }
    T& object ;
};

#define PASTE_TOKENS(a,b) a ## b
#define DO_PASTE_TOKENS(a,b) PASTE_TOKENS(a,b)
// C++0X
#define SCOPED_USE(a) scoped_use< decltype(a) > \
      DO_PASTE_TOKENS( _temp_scoped_use_helper_ , __COUNTER__ )(a) ;

std::vector<double> my_seq ;

int main()
{
    {
       SCOPED_USE( my_seq ) ;
       // use my_seq
       my_seq.reserve(1000) ;
       // etc
       std::cout << my_seq.capacity() << '\n' ;
    }
    std::cout << my_seq.capacity() << '\n' ;
}
vijayan121 1,152 Posting Virtuoso
#include <iterator>
#include <string> 

struct String_list
{
    struct iterator : std::iterator< std::bidirectional_iterator_tag, std::string >
    {
        explicit iterator( std::string* p ) : ptr(p) {}

        std::string& operator*() { return *ptr ; }
        // ...
        
        iterator& operator++ () { ++ptr; return *this ; }
        // ...

        // and so on for the other bidirectional iterator operations

        private: std::string* ptr;
    };

    // ....

};
vijayan121 1,152 Posting Virtuoso

Use inet_pton() in <arpa/inet.h> (Unix) or Ws2tcpip.h (Windows Vista+)
http://www.kernel.org/doc/man-pages/online/pages/man3/inet_pton.3.html
to convert the IPv6 address string and place it in a in6_addr struct. This struct has a union where the address can be viewed as an array of 16 octets.

const std::string& address_string = "fe80::202:b3ff:fe1e:8329" ;
    in6_addr address ;
    enum { NBYTES = sizeof(address._S6_un._S6_u8) } ;
    
    if( inet_pton( AF_INET6, address_string.c_str(), &address ) == 1 )
    {
        std::cout << address_string << "\nbytes (hex): " << std::hex ;
        std::for_each( address._S6_un._S6_u8, address._S6_un._S6_u8 + NBYTES,  
                       []( unsigned char byte ) { std::cout << byte << ' ' ; } ) ; 
        std::cout << '\n' << std::dec ;
    }
    else std::cout << "badly formed address string: " << address_string << '\n' ;
vijayan121 1,152 Posting Virtuoso

But I guess your example would fall under POD when the new standard comes in.

Not too sure about that mike. AFAIK, this is how it stands as of now:

9.5 A trivially copyable class is a class that:
- ...<elided>
- has a trivial destructor

12.4 A destructor is trivial if it is neither user-provided nor deleted and if: ...<elided>

9.5 A trivial class is a class that has a trivial default constructor and is trivially copyable.

9.9 A POD struct is a class that is both a trivial class and a standard-layout class, and has ... <elided>

vijayan121 1,152 Posting Virtuoso

There is a typo on line 74. Should be my_size = size ; Also, in your operator=(), you need to check for a trivial self-assignment. http://yosefk.com/c++fqa/assign.html

vijayan121 1,152 Posting Virtuoso

The catch() does not match the type of the exception that is thrown.

Either:

try 
    {
        std::ifstream somefile(argv[1], std::ios::in|std::ios::binary ) ;
        if( !file ) throw "Error opening file!" ; 

        // no error
        // ...
    }

    catch( const char* cstr )
    {
        std::cerr << cstr << '\n' ;
    }

or

try 
    {
        std::ifstream somefile(argv[1], std::ios::in|std::ios::binary ) ;
        if( !file ) throw std::ios::failure( "Error opening file!" ) ; 
        
        // no error
        // ...
    }
    catch( const std::exception& e )
    {
        std::cerr << e.what() << '\n' ;
    }

would be ok.

vijayan121 1,152 Posting Virtuoso

You are basically asking the person who reads your code to be aware of "value-initialization of POD type means zero-initialization". This is not so common (many people wouldn't even know the difference between default-initialization and value-initialization).

I would expect that anyone who has used a standard library container like std::vector<> would be aware of what value-initialization means. (However, it is still a good idea to make the initialization explicit.)

Incidentally, a non-POD can also be value initialized if it does not have a (has a trivial) constructor. eg.

struct not_pod
{
    ~not_pod() {}
    
    private: int a[5] ;
};
vijayan121 1,152 Posting Virtuoso

For a dynamically allocated array with new T[N] , N must be non-negative; it may evaluate to zero. When N is zero, an array with no elements is allocated and a distinct non-null pointer to it is returned. This array with no elements is deleted normally; with delete[]

vijayan121 1,152 Posting Virtuoso

Consider making your print functions const-correct. void cProg3::Print_s() const etc.

There are many ways to print out the elements in an STL sequence.
You could iterate through the sequence (as you have done). You could use a standard algorithm along with a function object (or a lambda function if you are using a newer compiler eg. Microsoft 2010).

#include <list>
#include <algorithm>
#include <functional>

struct cProg3 { /*...*/ void print_s() const { /*...*/ } /*...*/ } ;

void print_list_one( const std::list<cProg3>& lst )
{
    for( std::list<cProg3>::const_iterator iter = lst.begin() ;
          iter != lst.end() ; ++iter ) iter->print_s() ;
}

void print_list_two( const std::list<cProg3>& lst )
{ std::for_each( lst.begin(), lst.end(), std::mem_fun_ref(&cProg3::print_s) ) ; }


void print_list_three( const std::list<cProg3>& lst )
{ std::for_each( lst.begin(), lst.end(), []( const cProg3& c ) { c.print_s() ; } ) ; }
vijayan121 1,152 Posting Virtuoso

Well, technically a Winxx console is not a window (though its input/output is managed by the Winxx subsystem) and can never be the recipient of Winxx 'focus'. SetFocus() and the like do not work with consoles.

The OS has nothing to do with focus (or with windows for that matter). Focus policies ("focus follows click", "focus follows mouse", "sloppyfocus" etc) are implemented by window managers. For example on X11, different focus models are used by different window managers.

vijayan121 1,152 Posting Virtuoso

Just create a console application (linker option /SUBSYSTEM:CONSOLE) and write your normal gui code. (Both use the same Win32 or Win64 environment subsystem).

You will have a Console created for you and a main() with stdin, stdout and stderr initialized correctly. Use GetModuleHandle(), GetStartupInfo() etc. if you need the parameters that would have been passed to a WinMain.

#include <iostream>
#include <windows.h>

long __stdcall WindowProcedure( HWND window, unsigned int msg, WPARAM wp, LPARAM lp )
{
    switch(msg)
    {
        case WM_DESTROY:
            std::cout << "\ndestroying window\n" ;
            PostQuitMessage(0) ;
            return 0L ;
        case WM_LBUTTONDOWN:
            std::cout << "\nmouse left button down at (" << LOWORD(lp)
                      << ',' << HIWORD(lp) << ")\n" ;
            // fall thru
        default:
            std::cout << '.' ;
            return DefWindowProc( window, msg, wp, lp ) ;
    }
}

int main()
{
    std::cout << "hello world!\n" ;
    const char* const myclass = "myclass" ;
    WNDCLASSEX wndclass = { sizeof(WNDCLASSEX), CS_DBLCLKS, WindowProcedure,
                            0, 0, GetModuleHandle(0), LoadIcon(0,IDI_APPLICATION),
                            LoadCursor(0,IDC_ARROW), HBRUSH(COLOR_WINDOW+1),
                            0, myclass, LoadIcon(0,IDI_APPLICATION) } ;
    if( RegisterClassEx(&wndclass) )
    {
        HWND window = CreateWindowEx( 0, myclass, "title",
                   WS_OVERLAPPEDWINDOW, CW_USEDEFAULT, CW_USEDEFAULT,
                   CW_USEDEFAULT, CW_USEDEFAULT, 0, 0, GetModuleHandle(0), 0 ) ;
        if(window)
        {
            ShowWindow( window, SW_SHOWDEFAULT ) ;
            MSG msg ;
            while( GetMessage( &msg, 0, 0, 0 ) ) DispatchMessage(&msg) ;
        }
    }
}
vijayan121 1,152 Posting Virtuoso
int numerator, denominator ;
    char slash ;

    // std::cin >> std::skipws // this is the default
    if( ( std::cin >> numerator >> slash >> denominator ) && ( slash == '/' ) )
    {
        // ok
    }
    else
    {
        // error in input
    }
vijayan121 1,152 Posting Virtuoso

Consider using a named constant to replace the 'magic number' 26 whic appears at several places in your code.What would you do if you need to modify your program to deal with 100-digit integers tomorrow?

enum { NDIGITS = 26, LAST_DIGIT = NDIGITS-1 } ;

I know that I can use a count variable to right justify these numbers like the professor wants, i just cannot for the life of me figure out how to implement it or how to do it a different way.

Just modify your print function to print a space when leading zeros are encountered.

void printarray( int arg[] )
{
    int i = 0 ;
    for( ; i<LAST_DIGIT && arg[i]==0 ; ++i ) std::cout << ' ' ;
    for( ; i<LAST_DIGIT ; ++i ) std::cout << arg[i] ;
    std::cout << arg[LAST_DIGIT] << '\n' ; // print the last digit even if it is zero
}
vijayan121 1,152 Posting Virtuoso

which is usually preffered and why?

Both book::book( int, string, double); and book::book( int data1, string name1, double data2); are indicative of poor programming style; one could argue that the second version is the worse one because it introduces meaningless noise words.

Well written code is self-documenting; the basic idea is to make source code easier to read and easier to understand.

Something like book::book( int num_pages, const std::string& author, double price); where formal parameter names convey meaning is generally preferred.

vijayan121 1,152 Posting Virtuoso

will c++ let you open a .exe or any file for that matter in binary mode?

Yes.

what would be the most efficient way of scanning thru a file on disk

Don't do any conversion to hex or any other text format; just compare the raw bytes.

#include <fstream>
#include <iterator>
#include <algorithm>

typedef unsigned char byte ;

bool is_byte_seq_present_in_file( const char* file_path,
                        const byte* byte_array, std::size_t array_size )
{
    // 1. open the file in binary mode
    std::ifstream file( file_path, std::ios::binary ) ;

    // 2. create a pair of iterators to iterate over the sequence of bytes in the file
    std::istream_iterator<byte> begin(file), end ;

    // 3. use std::search() to search for the byte sequence in the file
    return std::search( begin, end, byte_array, byte_array+array_size ) != end ;
}
vijayan121 1,152 Posting Virtuoso

First, a couple of suggestions regarding your coding style. I'm taking int GetNumber(std::string number) as an exmple. The comments are inline, and some of them would apply to the rest of your code as well.

// for user defined types, prefer passing by reference-to-const over passing by value
int GetNumber( const std::string& number )
{
    // static - needs to be initialized only once
    // const - just being const-correct
    // avoiding magic numbers eg. words[31], for( int i=0 ; i<31; ++i ) etc.
    static const std::string words[] = {"one", "two", "three", "four", "five", 
        "six", "seven", "eight", "nine", "ten", "eleven", "twelve", "thirteen", 
        "fourteen", "fifteen", "sixteen", "seventeen", "eighteen","nineteen", 
        "twenty", "thirty", "fourty", "fifty", "sixty", "seventy", "eighty", 
        "ninety","hundred", "thousand", "million", "billion" } ;

    // an extra zero added at the end of numbers[] 
    // to avoid special casing when 'number' is not in 'words[]'.
    static const int numbers[] = { 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 
        15, 16, 17, 18, 19, 20,30, 40, 50, 60, 70, 80, 90, 100,
        1000, 1000000, 1000000000, 0 } ;

    enum { N = sizeof(words)/sizeof(*words), M = sizeof(numbers)/sizeof(*numbers) - 1 } ;

    // just making sure that we have not inadvertently omitted something
    // a compile-time assertion that the number of elements are in sync.
    typedef char N_must_be_equal_to_M_here[ N == M ] ; // C++98
    //static_assert( N==M, "N_must_be_equal_to_M_here") ; // C++1X

    // why write a loop (where it's easy to make a careless mistake or a typo)
    // when …
vijayan121 1,152 Posting Virtuoso

If there was a "return", I could do it that way, but there isn't.

Create a class ElectionResults_test_driver .

Add a friend declaration friend class ElectionResults_test_driver ; to ElectionResults .

Let the test driver examine the innards of ElectionResults after each test case.

vijayan121 1,152 Posting Virtuoso

You need to create a 'copy on write' view.

Open the file for read access: CreateFile( ...., GENERIC_READ, .... ) ; Create the FileMapping for read access: CreateFileMapping( ....., PAGE_READONLY, ..... ) ; Create a copy-on-write view: MapViewOfFile( ......, [b]FILE_MAP_COPY[/b], ..... ) ; Unix: mmap( ...., PROT_READ|PROT_WRITE, [b]MAP_PRIVATE[/b], .... ) ;

vijayan121 1,152 Posting Virtuoso

I find the greatest common divisor of numerator and denominator.

You are right; there is no need to find individual factors at all. Just find the gcd and divide both the numerator and denominator by it.

This is slightly faster:

inline unsigned int gcd( unsigned int a, unsigned int b ) // Euclid
{ return b==0 ? a : gcd( b, a%b ) ; }
vijayan121 1,152 Posting Virtuoso

void is just the return type of the function; the actual argument is a pointer to such a function.

#include <iostream>
typedef void first_arg_fn_type( int*, void** ) ;
typedef int second_arg_fn_type( void**, int* ) ;
typedef void function_type( first_arg_fn_type*, second_arg_fn_type* ) ;
function_type* fnctn ;

void function_one( int*, void** ) { std::cout << "function_one( int*, void** )\n" ; }
int function_two( void**, int* ) { std::cout << "function_two( void**, int* )\n" ; }

void call_both( first_arg_fn_type* f1, second_arg_fn_type* f2 )
{
    std::cout << "call_both calling f1 => " ;
    f1(0,0) ;
    std::cout << "call_both calling f2 => " ;
    f2(0,0) ;
}


int main( int argc, char** argv )
{
    fnctn = &call_both ;
    first_arg_fn_type* pfn1 = &function_one ;
    second_arg_fn_type* pfn2 = &function_two ;
    fnctn( pfn1, pfn2 ) ;
}
vijayan121 1,152 Posting Virtuoso

You can check if a string is a palindrome without having to make a copy; just iterate from either end looking for a mismatch.

bool is_palindrome( const std::string& str )
{
    std::string::const_iterator mid = str.begin() + str.size() / 2 ;
    return !str.empty() &&
        std::mismatch( str.begin(), mid, str.rbegin() ).first == mid ;
}

And to be pedantically correct, you need a return statement after the while loop: return in.eof() && !out ? 0 : EXIT_FAILURE ;

vijayan121 1,152 Posting Virtuoso

No instructor I know teaches vectors first.

Stroustrup for one does.

mike_2000_17 commented: epic pwnage! +1
vijayan121 1,152 Posting Virtuoso

This is not beyond his level. There is no reason to learn arrays before vectors. Novices should learn vectors because they convey the same concept but are "easier"

Agreed, vectors are far easier to learn, with fewer chances to make errors.

vijayan121 1,152 Posting Virtuoso

void(*fnctn)(void(*)(int *,void **),int(*)(void**,int*)); is equivalent to:

typedef void first_arg_fn_type( int*, void** ) ;

   typedef int second_arg_fn_type( void**, int* ) ;

   typedef void function_type( first_arg_fn_type*, second_arg_fn_type* ) ;

   function_type* fnctn ;