![]() |
Алгоритмы обхода матрицы
Задача следующая. Есть матрица размера mxn
Нужно отсортировать элементы матрицы и пройти ее по часовой стрелке от начала до центра, располагая в матрице отсортированные ее элементы. Например, если дана матрица A(m,n) {a(i,j)-элементы} и m=n=3, то проход a(1,1) -> a(1,2) ->a(1,3) -> a(2,3) -> a(3,3) -> a(3,2) -> a(3,1) -> a(2,1) --> a(2,2) Насколько эффективен будет следующий алгоритм обхода: сначала делаем поворот (с располаганием элементов) на 3 четверти, затем циклично до конца повороты на 2 четверти. Какие более эффективные алгоритмы можно использовать? Код:
'Расположить элементы матрицы по часовой стрелке в возрастающем порядке |
1. Хорошо бы иметь таблицу преобразования (ТП) между координатами элемента в матрице и положением в одномерном массиве "раскрученной спирали", тогда заполнение выполняется за один проход... К примеру для матрицы 3x3 таблица преобразования будет (x,y) = {(1,2) (1,3) (2,3) (3,3) (3,2) (3,1) (2,1) (2,2)}, т.е. по сути это двумерный массив указателей.
2. Теперь как можно построить ТП. Допустим, мы можем построить ее для одного оборота обхода матрицы (MxN) начав с левого верхнего угла, т.е. имеем ф-цию Fun (N, M, I, J), добавляющую в конец глобальной ТП координаты обхода (I, J - "координаты" начала обхода). Так вот, полный путь состоит из последовательности: Fun (N,M, 0,0) --> Fun (N-2,M-2, 1,1) --> Fun (N-4,M-4, 2,2) ... пока размерность массива >0. 3. Алгоритм Fun (M, N, I, J) линеен и состоит из четырех отрезков: - y=J, x увеличивается от I до I+N-1 - x=I+N-1, y увеличивается от J до J+M-1 - y=J+M-1, x уменьшается от x=I+N-1 до I - x=I, y уменьшается от J+M-1 до J+1 З.Ы. Это только общий алгоритм... Звиняюсь, но из вашего кода я мало чего понял, и про "четверти" с "поворотами" тоже. |
Цитата:
Три четверти поворота это проход от a(1,1) до a(3,1) - по 2 строкам и столбцу В коде делается следующее. Задаются начальные значения позиции в матрице и конечные значения: 1. проход по первой строке (четверть от полного поворота по часовой стрелке от a(1,1) до a(1,1)). После каждой четверти поворота меняем начальные значения на конечные. Строка(y) фиксируется, столбцы(x) меняются. 2. проход по последнему столбцу (вторая четверть поворота). Столбец(x) фиксируется, строки(y) меняются. 3. проход по последней строке (четверть поворота - всего 3/4 поворота) Заводится цикл, зависящий от переменной, показывающей четный или нечетный проход, чтобы знать, надо ли уменьшать индексы или нет: 1. проход по столбцу 2. проход по строке После каждого полного поворота уменьшается счетчик, показывающий конечные значения По-моему вы предложили то же самое.. Есть ли еще какие-нибудь способы? |
есть, их полно. Правда чем дальме - тем более извращённый способ получается.
Например, сведём всё к одной операции прохода строчки и одной операции поворота матрицы (всё это в цикле). в цикле: 1. прошли верхнюю строчку 2. повернули на 90 CCW (кто фотошоп видел, поймёт) дальше варианты: копировать матрицу или поворачивать координатную ось. Дешевле повернуть ось (понятней - наоборот). Так и сделаем! Код:
// извиняюсь, что пишу не на языке вопроса, но если идея зацепит, попробую перевести |
Время: 01:26. |
Время: 01:26.
© OSzone.net 2001-