| Версия для печати темы
Нажмите сюда для просмотра этой темы в оригинальном формате |
| Форум программистов > C/C++: Для новичков > Конструкторы преобразования |
| Автор: o2n3e 19.8.2011, 17:45 | ||
| Здравствуйте! Я полный новичок в программировании, вернее в практической его части(теоретические знания имеются). Появилась возможность попрактиковаться, и тут же возникла загвоздка. Проблему решил сам, но решение мне не нравится, поэтому прощу направить на путь истинный. Задача: У нас есть http://ru.wikipedia.org/wiki/G-code. Они состоят из кадров, кадр - одна строка. В начале кадра указывается команда, потом параметры. Нужно хранить их в памяти программы для работы с ними, т.е. что-то типа массива классов, где класс - это один кадр. Варианты входящих параметров: g0 - это X или Y; g1 - это X или Y или Z или F, возможны любые комбинации из x,y,f; g2 - это x+y+i+j+f?; g3 - то же самое, что и g2; g4 - это x; g90 и g91 без параметров. Вот мой вариант:
http://pastebin.com/6G2j9FC4 Класс должен знать какая команда в него записана, и исходя из этого выполнять методы. т.е. если есть метод toString, то он должен возвращать x, если он g0\1x, либо xy, если он g0\1xy. Мне кажется, что можно сделать всё намного проще, но я не знаю как. От Qt тут только флаги, поэтому не стал писать в Qt раздел |
| Автор: bsa 19.8.2011, 17:52 |
| Для этого существуют виртуальные методы. Делаешь абстрактный базовый класс "кадр" с чисто виртуальным методом toString(), а все остальные делаешь его наследниками и определяешь этот самый метод. |
| Автор: o2n3e 19.8.2011, 20:57 | ||||
| Если делать классы типа G0, G1, etc..., то всё ровно надо будет городить огород в методах. Если делать все возможные варианты наследниками - это будет бида, т.е. будет over10 разных классов. Что-то типа такого?
По мне так проще сделать:
Объясните пожалуйста, в чем смысл? Так же, я задавал вопрос в основном именно про конструкторы. Можно ли избавиться от этих монстрозаумных громадин? |
| Автор: alexvs11 19.8.2011, 22:06 | ||
можно замутить чтото вроде
|
| Автор: bsa 20.8.2011, 23:09 |
Во-первых, лучше делать так: out += QString::number(px); //имхо, короче и быстрей работает. Во-вторых, а ты что думал? Если хочешь, чтобы у объектов были одни рычаги управления, но разное поведение, то делай через виртуальные методы. Все остальное будет работать медленней. В-третьих, сделав так, у тебя получится, что у каждого класса только один конструктор. |
| Автор: o2n3e 21.8.2011, 02:15 | ||
| Спасибо, исправил. Допустим, если взять пример тов. alexvs11, то у нас получится 17 разных вариантов каждого метода. В чём профит от щаблонов? Имхо, так быстрее, понятней и меньше код"а.
Но мне это как-то не нравится, хотя и лучше моего варианта. Ведь можно как-то сделать проще. Сижу ломаю голову... |
| Автор: mes 21.8.2011, 11:33 | ||
аргументы могут быть только одного типа ? Добавлено через 2 минуты и 35 секунд т.е. как я понял Вам надо преобразовать одно или несколько аргументов в строку в зависимости от кода .. тогда вопрос Вам нужен жесткий статический контроль на соблюдение соответсвия кода передаваемым аргументам ? Добавлено через 8 минут и 29 секунд в этом случае все сводится к написанию функции для каждого кода.. т.е.
|
| Автор: mes 21.8.2011, 12:01 |
| если ж достаточно динамического контроля, то можно так : http://liveworkspace.org/code/1d33a0600475b74e75b1703ee0504d47 это правда с использованием C++0x, но можно и вручную получить примерное.. |
| Автор: o2n3e 21.8.2011, 15:33 | ||||||||
Cтроки вида: G0X500.500Y500.500 G3X500.500Y500.500I500.500J500.500F500.500 Не совсем, нужно сделать что-то типа контейнера для кадров, и интерфейс к нему. Кадров может быть больше тысячи в одной программе. Архитектура программы: Я беру и парсю входящую строку, и передаю получившиеся значения в конструктор класса. Класс добавляется, допустим, в вектор базового класса. И потом уже работаю с кадрами, путём перебора вектора. Как в примере тов. Alexvs11. Допустим, запись в файл всех слайсов:
Так же со смешением, масштабирование, интерполяцией.
В яблочко. Я хочу сделать удобное хранилище/обработчик этих самых кодов. С удобным интерфейсом.
Да. Код кадра указывает на количество аргументов, аргументы всегда имеют одну и туже последовательность, что на входе, что на выходе. Поэтому, если на конструктор приходит: float first, float second и код кадра G0XY, то first - это 100% X, а second - это 100% Y. |
| Автор: mes 21.8.2011, 17:09 | ||||||
с вектором понятно.. если можно удобно работать с фреймом отдельно, то и с их массивом проблем не составит
значит статический контроль не нужен, так как на вход попадает уже в сторковом виде.. т.е. надо строку преобразовать к "код + аргументы" и иметь возможность преобразовать это обратно к строке.. тут понятно.. теперь вопрос по аргументам, их я как понимаю фиксированное кол-во, при этом какие аргументы будут переданы задается кодом , плюс у каждого имени аргумента есть очередность..
т.е. как говорите Y может быть на первом месте только если нет Х.. так ? Добавлено через 5 минут и 25 секунд если присмотреться к значением , то видно что аргументы представлены битовыми значениями.. т.е. правильней не делать перечисление всех вариантов команд, а разбить на составляющие. тогда G0xy = gcode::make_cmd(gcode::g0, gcode::x | gcode::y); Добавлено через 7 минут угу, кол-во вариантов аргуметов получается заранее известно.. Добавлено через 9 минут и 50 секунд теперь как этот фрейм предполагается использовать ? имеется ввиду обработка команд, а не превращение его опять в строку.. |
| Автор: mes 21.8.2011, 17:27 | ||||
пока из сказанного видится такая структура самого фрейма:
флаги отделены от аргументов для экономии памяти.. Добавлено @ 17:35 парсер : читает команду (G3) ищет соотвествующее ей значение в карте и устанавливает код фрейма после в цикле читает имя аргумента и его значение и устанавливает соответсвующий флаг и переменную.. тогда для удобной работы нам нужен mapper как посредник между строковым видом и данными..
Добавлено через 14 минут и 59 секунд тут недостаток в статичности структуры, что не позволяет легкого расширения.. но зато повышается скорость обработки, так что если кол-во аргуметов фиксировано, то все в порядке.. |
| Автор: mes 21.8.2011, 17:52 | ||||||||
помимо этого нужен еще читатель (из строки или потока)
тогда парсер условно будет выглядить так :
или даже так :
Добавлено @ 18:04
посмотрел на остальные енумы комманд, законномерность, увы, не подтвердилась.. но это не отменяет остальных умозаключений и кода.. |
| Автор: mes 21.8.2011, 18:08 |
| сейчас сдеривающим является ответ на этот вопрос : Добавлено через 8 минут и 12 секунд а также интересны ограничения на компилятор .. можно ли использовать C++0x ? Добавлено через 12 минут и 8 секунд тут точно опечатки нет ? |
| Автор: o2n3e 21.8.2011, 18:46 | ||||
Числа в енуме вообще не имеют смысла.
Исключая текстовые операции и редактирование, Одна из самых сложных задач - это нарисовать этот самый г-код. Но пока до этого я не добрался. Добавлено через 5 минут и 24 секунды
Ограничение на тулкиты и компилятор нет, компилятор используется gcc-4.5.2. Эти константы взяты из протокола обмена с контроллером, с которым общается данная программа по com-порту. Никакой смысловой нагрузки они не несут, кроме того, что их нужно использовать для работы с контролером. Допустим кадр G1X500.500Y500.500, в формате, который понимает контроллер, выглядит так: C07500870007A31400870007A314. |
| Автор: mes 21.8.2011, 18:52 |
понятно.. т.е привод в машинозависимый вид нас не интересует.. Добавлено @ 18:59 в частности меня интересует вопрос как поступать с аргументами.. конечно самый простой способ передавать исполняющей функции весь набор флагов и аргументов и чтоб функция сама проверяла нужные.. но с другой стороны можно похимичить и связывать функцию с нужным набором аргументов.. сейчас подумую как продемонстрировать, ибо на словах не очень понятно.. |
| Автор: mes 21.8.2011, 19:33 |
| подумав, все таки пришел к выводу что метод обработчик должен получать полный фрейм, тогда пример с использованием может выглядить так : http://liveworkspace.org/code/383ff2f954f6810b910a64c7564c4e30 |
| Автор: mes 21.8.2011, 19:56 |
| чтоб не загружать рантайм, так как связи с процессором постоянные, можно определить карту как статическую переменную... http://liveworkspace.org/code/8a0836e340090fb7f217bdfa8bd1e2e5 (для не C++0x нужно добавить статическую стурктуру-инициализер) |
| Автор: o2n3e 21.8.2011, 20:12 |
| тов. Mes, спасибо вам большое. Пытаюсь разобраться в вашем коде. |
| Автор: mes 21.8.2011, 23:09 |
| http://liveworkspace.org/code/7cf298a446aad6a67669a66b44a8c080 |