Форум: "Основная";
Текущий архив: 2008.10.12;
Скачать: [xml.tar.bz2];
Вниз
Кубик-рубик Найти похожие ветки
← →
@!!ex © (2008-01-11 11:07) [0]Задача реализовать кубик рубик...
Вопрос в том, как его лучше хранить и как вращать его части...
Пока ничего умнее вот такого:
Cube:array[0..3,0..3,0..5] of byte;
не придумал...
Но тогда вращение нужно реализовывать для 24!(6 сторон, на каждой по 4 вращения) случаев... и каждое отдельно... что мне не очень нравится..
← →
DVM © (2008-01-11 11:18) [1]
> Cube:array[0..3,0..3,0..5] of byte;
какой же это кубик?
← →
DrPass © (2008-01-11 11:20) [2]
> Cube:array[0..3,0..3,0..5] of byte
Мне всегда казалось, что кубик Рубика состоит из 26 элементов, и прекрасно описывается массивом [0..2,0..2,0..2] :)
← →
DVM © (2008-01-11 11:22) [3]
> и прекрасно описывается массивом [0..2,0..2,0..2]
Причем даже с большим избытком.
← →
Рамиль © (2008-01-11 11:23) [4]TCube = array[0..5, 0..2, 0..2] of TColor;
при вращении траспонируем матрицу 0..2, 0..2 соот. стороны и перекидываем ряды за гранью (или как точнее сказать то).
Навскидку както так.
← →
@!!ex © (2008-01-11 11:31) [5]> [1] DVM © (11.01.08 11:18)
0..2 естственно.
> [4] Рамиль © (11.01.08 11:23)
Не понял...
Объясни подробнее?
← →
Sandman25 (2008-01-11 13:50) [6]Можно хранить в виде трехмерной фигуры из 9 точек 6 цветов, тогда все повороты сводятся к стандартным.
← →
@!!ex © (2008-01-11 13:59) [7]> в виде трехмерной фигуры из 9 точек 6 цветов
Как это?
← →
Dib@zol © (2008-01-11 16:06) [8]А почему бы не прописать процедуру, скажем, Rotate, с двумя входными параметрами: индексом одного из 9-ти кубиков, которые надо повернуть, и направление вращения? И 24 случая отдельно расписывать не придётся. Максимум три.
← →
@!!ex © (2008-01-11 16:43) [9]> Rotate, с двумя входными параметрами: индексом одного из
> 9-ти кубиков, которые надо повернуть, и направление вращения?
Да я все никак не пойму как сделать... Уже весь мозг сломал...
← →
DrPass © (2008-01-11 16:52) [10]Каждый элемент массива [0..2,0..2,0..2] - запись, описывающая тип кубика (одно-, двух- или трехцветный) и его поворот относительно наблюдателя. При повороте грани меняешь в массиве положение кубиков, и пересчитываешь поворот в записи. Этой информации будет достаточно для построения изображения
← →
@!!ex © (2008-01-11 17:09) [11]> описывающая тип кубика (одно-, двух- или трехцветный) и
> его поворот относительно наблюдателя.
Ууу. гемор.. особенно с поворотом относительно наблюдателя... хотя тоже вариант...
← →
Sandman25 (2008-01-11 17:13) [12]@!!ex © (11.01.08 13:59) [7]
Центр куба имеет координаты (0,0,0); Верхняя грань - z=1, нижняя грань - z=-1; левая грань - x=-1; правая грань - x=1; дальняя грань - y=-1, ближняя грань - y=1. Соответственно, нпаример левый дальний угол верхней грани имеет координаты (-1,-1,1). Имеем корординаты 9 красных точек, 9 синих точек и т.д., всего 6 цветов. Повороты будут сводиться к неким линейным преобразованиям координат.
Хотя, возможно, лучше эту же идею использовать для хранения в виде обычного массива, но с координатами [-1..1,-1..1,-1..1], за счет симметрии можно будет уменьшить число вариантов.
← →
KilkennyCat © (2008-01-11 20:39) [13]a : array [0..2, 0..2] of TColor - плоскость
b : array [0..5] of a - все плоскости
Неизящно, но тупо и просто.
← →
@!!ex © (2008-01-11 21:32) [14]> [13] KilkennyCat © (11.01.08 20:39)
А вращать как?
← →
KilkennyCat © (2008-01-11 21:43) [15]
> @!!ex © (11.01.08 21:32) [14]
берем одну плоскость b[0]
ее вращение - это вращение матрицы а[0..2, 0..2]
к b[0] примыкают b[1], b[2], b[3], b[4]
значит, делаем обмен между их матрицами по первому столбу.
Вся фишка в прописывании каким образом что к чему прилегает. Алгоритм ваще-то максимум часа на четыре работы.
Предлагаю конкурс: кто напишет за эти выходные наиболее простой алгоритм вращения кубика.
← →
KilkennyCat © (2008-01-11 21:45) [16]а, Рамиль так же предложил, не заметил.
← →
KilkennyCat © (2008-01-11 21:46) [17]кстати, могу дать еще головоломную подсказку - кубик можно развернуть на плоскость.
← →
Sha © (2008-01-15 14:49) [18]> @!!ex © (11.01.08 11:07)
> Вопрос в том, как его лучше хранить и как вращать его части...
Надо сначала определиться, что для тебя значит "лучше" .
Если надо, чтобы было как можно меньше процедур вращения, то выбираешь 2 противоположных вершины куба и нумеруешь квадратики на каждой грани куба по часовой стрелке от 0 до 7, начиная с квадратика, содержащего вершину.
Центральный квадратик нумеровать не обязательно, т.к. при вращениях крест не меняет своего положения.
Объявляешь
TRubik = array[0..1] of array[0..2] of array[0..7] of byte;
или
TRubik = array[0..5] of array[0..7] of byte;
или
TRubik = array[0..1] of array[0..2] of integer;
или даже
TRubik = array[0..5] of integer;
и вперед.
Вроде должно быть достаточно написать всего 2 процедуры: одну для вращения по часовой стрелке, другую - против.
Если надо, чтобы процедуры вращения были простыми быстрыми, то
заметь, что в каждой вершине куба может находиться один из 8 различных миникубов-вершин и в каждом ребре - один из 12 различных миникубов-ребер.
При этом миникуб-вершина может иметь одну из трех возможных ориентаций: правильную, когда его минимальный цвет лежит на грани с минимальным цветом центрального квдратика, или неправильную (повернут на 120 или 240 градусов по часовой стрелке).
Аналогично, миникуб-ребро может иметь одну из двух возможных ориентаций: правильную, когда его минимальный цвет лежит на грани с минимальным цветом центрального квдратика, или неправильную (повернут на 180 градусов).
Объявляешь
TRubik = array[0..19] of array[0..7] of byte;
и вперед.
Потребуется написать 12 процедур: 6 для вращения по часовой стрелке, и 6 - против. Но он того стоит.
← →
Sha © (2008-01-15 14:52) [19]Сорри, скопипастил объяление :-(
В последнем случае должно быть TRubik = array[0..19] of byte;
Страницы: 1 вся ветка
Форум: "Основная";
Текущий архив: 2008.10.12;
Скачать: [xml.tar.bz2];
Память: 0.5 MB
Время: 0.041 c