Hello, here is the code, it seems to be written correctly, I write on CodeBlocks:

#include <vector> #include <algorithm> #include <iostream> using namespace std; template <class elemType> elemType& min (const std::vector<elemType> &vec) { typename std::vector<elemType>::iterator select = vec.begin(), it = next(select), end_it = vec.end(); for ( ; it != end_it; it++ ) { if ( *it < *select ) select = it; } return *select; }; int main() { int massiv[10] = {35, 66, 98, 15, 32, 41, 24, 90, 55, 100}; std::vector<int> vec_train(massiv,massiv+10); min(vec_train); return 0; } 

But it gives the following error:

error: conversion from 'std :: vector :: const_iterator {aka __gnu_cxx :: __ normal_iterator>}' to non-scalar type 'std :: vector :: iterator {aka __gnu_cxx :: __ normal_iterator>}' requested |

How can such errors be decoded by myself, if I just recently started learning programming? Thank.

    2 answers 2

    In the function, the parameter is defined as a constant reference.

     elemType& min (const std::vector<elemType> &vec) { ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ 

    Therefore, functions such as begin and end return an iterator of type const_iterator . Correct

     typename std::vector<elemType>::const_iterator select = vec.begin(), it = next(select), end_it = vec.end(); 

    You should also include the title.

     #include <iterator> 

    since the program uses the function std::next , declared in this header.

    Also keep in mind that the min function is incorrect, since in the general case the transmitted vector may be empty. And this means that the function has a call to a non-existing element of the vector and, accordingly, a dereferencing of an invalid iterator.

    There is a standard algorithm std::min_element , declared in the header <algorithm> , which performs the task.

    Your function can be determined by analogy with this algorithm. For example,

     #include <iostream> #include <vector> template <class elemType> auto min( const std::vector<elemType> &vec ) { auto select = vec.begin(); if ( select != vec.end() ) { for ( auto it = vec.begin(), end_it = vec.end(); ++it != end_it; ) { if ( *it < *select ) select = it; } } return select; } int main() { int massiv[] = { 35, 66, 98, 15, 32, 41, 24, 90, 55, 100 }; const size_t N = sizeof( massiv ) / sizeof( *massiv ); std::vector<int> vec_train( massiv, massiv + N ); auto it = min( vec_train ); if ( it != vec_train.end() ) { std::cout << "Minimum is " << *it << std::endl; } return 0; } 

    Outputting the program to the console

     Minimum is 15 

    If your compiler does not support the auto type specifier, the function can be defined as

     template <class elemType> typename std::vector<elemType>::const_iterator min( const std::vector<elemType> &vec ) { typedef typename std::vector<elemType>::const_iterator const_iterator; const_iterator select = vec.begin(); if ( select != vec.end() ) { for ( const_iterator it = vec.begin(), end_it = vec.end(); ++it != end_it; ) { if ( *it < *select ) select = it; } } return select; } 
    • Thank you so much for the detailed explanation! =) - FishTheBig
    • For the empty vector UB in the TC code, a little earlier dereference occurs - when you call next . By the way, std::min for the initialization list also has UB with an empty sequence. So it can be carried out in preconditions . - αλεχολυτ
     error: conversion from 'std::vector::const_iterator {aka __gnu_cxx::__normal_iterator >}' to non-scalar type 'std::vector::iterator {aka __gnu_cxx::__normal_iterator >}' requested 

    How can such errors be decoded by myself, if I just recently started learning programming?

    To begin with, from the text of the error it is necessary to throw out all unnecessary. In this case, remove the text in curly brackets with brackets. It refers to an internal compiler type iterator. "aka" means "also known as", i.e. essentially synonymous, alternate name. We get:

     error: conversion from 'std::vector::const_iterator' to non-scalar type 'std::vector::iterator' requested 

    Here you can see more clearly what the error says:

     запрошено преобразование из 'std::vector::const_iterator' в нескалярный тип 'std::vector::iterator' 

    A scalar type is in particular any arithmetic type, for example, double or int . Between these types, c ++ provides implicit conversions. Those. You can write, say:

     double d = 5.5; int i = d; 

    and the compiler will not give any errors to it. In your case, the type is non-scalar, which means that for an implicit conversion from one type of T1 to another, T2 must be defined:

    • or constructor for type T2 , taking an argument of type T1 ;
    • or a conversion operator in type Т1 type operator T2() .

    There are no std::vector::const_iterator conversions to std::vector::iterator (although it is worth noting that there is an inverse transformation), so the compiler produced an appropriate error.

    Well, about the elimination of the cause of the error is already described in detail in another answer, so I see no reason to repeat.