Форум программистов, компьютерный форум CyberForum.ru

Перегрузка std::end для двумерного массива - C++

Восстановить пароль Регистрация
 
rikimaru2013
C++ Game Dev
 Аватар для rikimaru2013
2135 / 968 / 223
Регистрация: 30.11.2013
Сообщений: 3,239
06.07.2016, 21:40     Перегрузка std::end для двумерного массива #1
Добрый день,

1) почему если закомментировать переопределение функций begin, end работает, ведь там явно не одномерный, а стандартный begin/end имеет шаблонное определение размерности
2) почему не могу всё же переопределить для base_range for и некоторых STL алгоритмов

C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
#include <algorithm>
#include <ctime>
#include <iostream>
using namespace std;
 
namespace std
{
 
    template <typename T, size_t M, size_t N>
    typename remove_all_extents<T>::type*
    begin( T( &array )[ M ][ N ] )
    {
        return begin( array[ 0 ] );
    }
 
    template <typename T, size_t M, size_t N>
    typename remove_all_extents<T>::type*
    end( T( &array )[ M ][ N ] )
    {
        return &array[ M-1 ][ N ];
    }
}
int main()
{
    const int sizeM = 2;
    const int sizeN = 3;
    srand( time( 0 ) );
 
    int arr[ sizeM ][ sizeN ];
 
    std::generate( std::begin( arr ), std::end( arr ), [](){ return rand() % 20 ;} );
 
    cout << endl;
    std::for_each( std::begin( arr ), std::end( arr ), []( int current ){ cout << current << " ";   } );
 
    for( auto& it : arr )
        cout << &it << " ";
 
    auto it = std::unique( std::begin( arr ), std::end( arr ), std::less<int>() );
    bool is = it == std::end( arr );
 
    cout << endl;
    std::for_each( it, std::end( arr ), []( int current ){ cout << current << " ";  } );
}
После регистрации реклама в сообщениях будет скрыта и будут доступны все возможности форума.
Хрисипп
 Аватар для Хрисипп
17 / 27 / 8
Регистрация: 09.02.2016
Сообщений: 212
06.07.2016, 23:49     Перегрузка std::end для двумерного массива #2
но вывод-то разный? и что это за компилятор такой?
nonedark2008
624 / 502 / 92
Регистрация: 28.07.2012
Сообщений: 1,341
07.07.2016, 01:13     Перегрузка std::end для двумерного массива #3
Цитата Сообщение от rikimaru2013 Посмотреть сообщение
и некоторых STL алгоритмов
Предположу, что некоторые STL алгоритмы хавают внутри себя iterator_traits...

Цитата Сообщение от rikimaru2013 Посмотреть сообщение
почему если закомментировать переопределение функций begin, end работает, ведь там явно не одномерный, а стандартный begin/end имеет шаблонное определение размерности
Можно по внятнее и поподробнее про проблему?

Добавлено через 22 минуты
Цитата Сообщение от rikimaru2013 Посмотреть сообщение
почему не могу всё же переопределить для base_range for
Ну, похоже компилятор для массивов реализует base range for отдельно от STL.
Это подтверждается тем, что его можно использовать без подключения каких-либо заголовков.
В интернете винят во всем ADL.
avgoor
562 / 352 / 83
Регистрация: 05.12.2015
Сообщений: 1,137
07.07.2016, 01:54     Перегрузка std::end для двумерного массива #4
rikimaru2013, Потому, что это UB:
17.6.4.2.1 Namespace std
1
The behavior of a C++ program is undefined if it adds declarations or definitions to namespace std or to a namespace within namespace std unless otherwise specified. A program may add a template specialization for any standard library template to namespace std only if the declaration depends on a user-defined type and the specialization meets the standard library requirements for the original template and is not explicitly prohibited.
GbaLog-
07.07.2016, 08:28
  #5

Не по теме:

Цитата Сообщение от Хрисипп Посмотреть сообщение
и что это за компилятор такой?
Любой компилятор из самых известных(g++,clang,vc++) скомпилирует этот код, к чему этот вопрос вообще?

nonedark2008
07.07.2016, 11:07     Перегрузка std::end для двумерного массива
  #6

Не по теме:

Цитата Сообщение от GbaLog- Посмотреть сообщение
Любой компилятор из самых известных(g++,clang,vc++) скомпилирует этот код, к чему этот вопрос вообще?
К тому, что как и сказал avgoor, это UB.
И на разных компиляторах это может работать по разному, либо вовсе не работать.
Это видно хоть по тому, что для range based for перегруженные методы не вызываются вовсе, хотя по логике должны.

Yandex
Объявления
07.07.2016, 11:07     Перегрузка std::end для двумерного массива
Ответ Создать тему
Опции темы

Текущее время: 12:08. Часовой пояс GMT +3.
КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin® Version 3.8.9
Copyright ©2000 - 2016, vBulletin Solutions, Inc.
Рейтинг@Mail.ru