Russian Qt Forum
Ноябрь 27, 2024, 06:14 *
Добро пожаловать, Гость. Пожалуйста, войдите или зарегистрируйтесь.
Вам не пришло письмо с кодом активации?

Войти
 
  Начало   Форум  WIKI (Вики)FAQ Помощь Поиск Войти Регистрация  

Страниц: 1 ... 11 12 [13]   Вниз
  Печать  
Автор Тема: Как писать ООП программы?  (Прочитано 86823 раз)
8Observer8
Гость
« Ответ #180 : Март 01, 2014, 09:30 »

Воспользуйтесь typedef'ами, с ними значительно понятней.
Вот то, что нужно! Видно сразу силу пространств имём, умных указателей и typedef'ов Улыбающийся

могу ли я себе позволить не удалять объекты выделенные динамически?
Сможете, главное не забыть удалить их потом.

А где их тогда удалить в этом примере:

Код
C++ (Qt)
#include <QApplication>
#include "shape.h"
#include "rectangle.h"
#include "circle.h"
#include "triangle.h"
#include "viewer.h"
#include <utility>
#include <memory>
#include <QDebug>
 
int main(int argc, char *argv[])
{
   QApplication a(argc, argv);
 
   Viewer viewer;
   viewer.resize(400, 200);
 
   myShapes::Triangle *pt = new myShapes::Triangle(30.0, 50.0);
   myShapes::Circle *pc = new myShapes::Circle(50.0);
   myShapes::Rectangle *pr1 = new myShapes::Rectangle(100.0, 25.0);
   myShapes::Rectangle *pr2(new myShapes::Rectangle(100.0, 25.0));
 
//    std::shared_ptr<myShapes::Triangle> pt(new myShapes::Triangle(30.0, 50.0));
//    std::shared_ptr<myShapes::Circle> pc(new myShapes::Circle(50.0));
//    std::shared_ptr<myShapes::Rectangle> pr1(new myShapes::Rectangle(100.0, 25.0));
//    std::shared_ptr<myShapes::Rectangle> pr2(new myShapes::Rectangle(100.0, 25.0));
 
   viewer.addForPainting(pt);
   viewer.addForPainting(pc);
   viewer.addForPainting(pr1);
   viewer.addForPainting(pr2);
 
   viewer.show();
 
   pc->setRadius(25.0);
 
   return a.exec();
}
 
Записан
8Observer8
Гость
« Ответ #181 : Март 01, 2014, 09:36 »

Воспользуйтесь typedef'ами, с ними значительно понятней.
Код
C++ (Qt)
#include <QApplication>
#include "shape.h"
#include "rectangle.h"
#include "circle.h"
#include "triangle.h"
#include "viewer.h"
#include <utility>
#include <memory>
#include <QDebug>
 
namespace myShapes
{
 
typedef std::shared_ptr<Triangle> TrianglePtr;
typedef std::shared_ptr<Circle> CirclePtr;
typedef std::shared_ptr<Rectangle> RectanglePtr;
 
}
 
using namespace myShapes;
 
int main(int argc, char *argv[])
{
   QApplication a(argc, argv);
 
   Viewer viewer;
   viewer.resize(400, 200);
 
   TrianglePtr pt(new myShapes::Triangle(30.0, 50.0));
   CirclePtr pc(new myShapes::Circle(50.0));
   RectanglePtr pr1(new myShapes::Rectangle(100.0, 25.0));
   RectanglePtr pr2(new myShapes::Rectangle(100.0, 25.0));
 
   viewer.addForPainting(pt);
   viewer.addForPainting(pc);
   viewer.addForPainting(pr1);
   viewer.addForPainting(pr2);
 
   viewer.show();
 
   pc->setRadius(25.0);
 
   return a.exec();
}
 

Уточнить имена нужно:
Код
C++ (Qt)
   myShapes::TrianglePtr pt(new myShapes::Triangle(30.0, 50.0));
   myShapes::CirclePtr pc(new myShapes::Circle(50.0));
   myShapes::RectanglePtr pr1(new myShapes::Rectangle(100.0, 25.0));
   myShapes::RectanglePtr pr2(new myShapes::Rectangle(100.0, 25.0));
 
Записан
Old
Джедай : наставник для всех
*******
Offline Offline

Сообщений: 4350



Просмотр профиля
« Ответ #182 : Март 01, 2014, 09:53 »

А где их тогда удалить в этом примере:
Например, в деструкторе Viewer.
Записан
Old
Джедай : наставник для всех
*******
Offline Offline

Сообщений: 4350



Просмотр профиля
« Ответ #183 : Март 01, 2014, 09:54 »

Уточнить имена нужно:

Мы же разрешили это пространство имен:
Код
C++ (Qt)
using namespace myShapes;
 
Записан
8Observer8
Гость
« Ответ #184 : Март 01, 2014, 10:03 »

Уточнить имена нужно:
Мы же разрешили это пространство имен:
Код
C++ (Qt)
using namespace myShapes;
 

А да, извените, не заметил Улыбающийся

А где их тогда удалить в этом примере:
Например, в деструкторе Viewer.

Да, похоже, это правильный ответ. Но что плохого в том, что мы НЕ будем применять delete к объектам? В моём приложении объекты в любом случае живут до конца, хоть это умный указатель, хоть особождение в деструкторе Viewer. Ведь при завершении приложения вся память возвращается системе.

Код
C++ (Qt)
#include <QApplication>
#include "shape.h"
#include "rectangle.h"
#include "circle.h"
#include "triangle.h"
#include "viewer.h"
#include <utility>
#include <memory>
#include <QDebug>
 
int main(int argc, char *argv[])
{
   QApplication a(argc, argv);
 
   Viewer viewer;
   viewer.resize(400, 200);
 
   myShapes::Triangle *pt = new myShapes::Triangle(30.0, 50.0);
   myShapes::Circle *pc = new myShapes::Circle(50.0);
   myShapes::Rectangle *pr1 = new myShapes::Rectangle(100.0, 25.0);
   myShapes::Rectangle *pr2(new myShapes::Rectangle(100.0, 25.0));
 
//    std::shared_ptr<myShapes::Triangle> pt(new myShapes::Triangle(30.0, 50.0));
//    std::shared_ptr<myShapes::Circle> pc(new myShapes::Circle(50.0));
//    std::shared_ptr<myShapes::Rectangle> pr1(new myShapes::Rectangle(100.0, 25.0));
//    std::shared_ptr<myShapes::Rectangle> pr2(new myShapes::Rectangle(100.0, 25.0));
 
   viewer.addForPainting(pt);
   viewer.addForPainting(pc);
   viewer.addForPainting(pr1);
   viewer.addForPainting(pr2);
 
   viewer.show();
 
   pc->setRadius(25.0);
 
   return a.exec();
}
 
Записан
8Observer8
Гость
« Ответ #185 : Март 01, 2014, 14:14 »

Плюс shared_ptr ещё в том, что пользователю (класса Viewer) не нужно бояться, что viewer удалит объект через указатель Улыбающийся
Записан
8Observer8
Гость
« Ответ #186 : Март 02, 2014, 08:12 »

Помогите, пожалуйста, разобраться почему не стирается старое изображение?



Когда я меняю радиус:

main.cpp
Код
C++ (Qt)
#include <QApplication>
#include "shape.h"
#include "rectangle.h"
#include "circle.h"
#include "triangle.h"
#include "viewer.h"
#include <utility>
#include <memory>
#include <QDebug>
 
namespace myShapes
{
 
typedef std::shared_ptr<Triangle> TrianglePtr;
typedef std::shared_ptr<Circle> CirclePtr;
typedef std::shared_ptr<Rectangle> RectanglePtr;
 
}
 
using namespace myShapes;
 
int main(int argc, char *argv[])
{
   QApplication a(argc, argv);
 
   Viewer viewer;
   viewer.resize(400, 200);
 
   TrianglePtr pt(new myShapes::Triangle(30.0, 50.0));
   CirclePtr pc(new myShapes::Circle(50.0));
   RectanglePtr pr1(new myShapes::Rectangle(100.0, 25.0));
   RectanglePtr pr2(new myShapes::Rectangle(100.0, 25.0));
 
   viewer.addForPainting(pt);
   viewer.addForPainting(pc);
   viewer.addForPainting(pr1);
   viewer.addForPainting(pr2);
 
   viewer.show();
 
   pc->setRadius(25.0);
 
   return a.exec();
}
 

Как в функции перерисовки стереть старое изображение?

viewer.cpp
Код
C++ (Qt)
#include "viewer.h"
#include <utility>
#include <QDebug>
 
Viewer::Viewer(QWidget* pwgt) :
   QGLWidget(pwgt)
{
}
 
void Viewer::draw(std::shared_ptr<myShapes::Shape> ps, int xOffset, int yOffset)
{
   glPointSize(2.0);
   glBegin(GL_LINE_LOOP);
   glColor3f(0.0, 0.0, 0.0);
   for (int i = 0; i < ps->amountOfPoints(); ++i) {
       std::pair<int, int> point = ps->point(i);
//        qDebug() << "x = " << point.first << "; xOffset = " << xOffset;
//        qDebug() << "y = " << point.second << "; yOffset = " << yOffset;
       int x = point.first + xOffset;
       int y = point.second + yOffset;
       glVertex2f(x, y);
   }
//    qDebug() << "";
   glEnd();
}
 
/*virtual*/ void Viewer::initializeGL()
{
   qglClearColor(Qt::white);
}
 
/*virtual*/ void Viewer::resizeGL(int nWidth, int nHeight)
{
   glMatrixMode(GL_PROJECTION);
   glLoadIdentity();
   glViewport(0, 0, (GLint)nWidth, (GLint)nHeight);
   glOrtho(0, 400, 200, 0, -1, 1);
}
 
/*virtual*/ void Viewer::paintGL()
{
   glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
 
   int xGeneralOffset = 50;
   int yGeneralOffset = 100;
   int xOffset = 0;
   int yOffset = 0;
   for (std::size_t i = 0; i < m_pshapes.size(); ++i) {
       if (( (i+1) % 2) != 0) { // Odd, one-based
           xOffset = xGeneralOffset;
           yOffset += yGeneralOffset;
       } else {
           xOffset = xGeneralOffset + 150;
       }
       if (i == 0 || i == 1) {
           yOffset = 50;
       }
       draw(m_pshapes[i], xOffset, yOffset);
   }
}
 
Записан
8Observer8
Гость
« Ответ #187 : Март 02, 2014, 08:17 »

Вот весь проект: https://github.com/8Observer8/Shapes/tree/drawingShapes
Записан
Igors
Джедай : наставник для всех
*******
Offline Offline

Сообщений: 11445


Просмотр профиля
« Ответ #188 : Март 02, 2014, 08:25 »

Но что плохого в том, что мы НЕ будем применять delete к объектам? В моём приложении объекты в любом случае живут до конца, хоть это умный указатель, хоть особождение в деструкторе Viewer. Ведь при завершении приложения вся память возвращается системе.
Так развивайте архитектуру, заводите класс "сцена", который будет хранить созданные объекты, загружать/выгружать их в файл и др. В этом и состоит основная работа: спроектировать хорошие классы, наладить их четкое взаимодействие. А лепить глобалы в main то так, "поменяйте мне подгузник"  Улыбающийся
Записан
Igors
Джедай : наставник для всех
*******
Offline Offline

Сообщений: 11445


Просмотр профиля
« Ответ #189 : Март 02, 2014, 08:38 »

Помогите, пожалуйста, разобраться почему не стирается старое изображение?
Circle::calcCoordinates должна сначала очистить вектор точек, а потом его заполнить

Как в функции перерисовки стереть старое изображение?
По умолчанию машина рисования сама стирает все перед каждым новым paint
Записан
8Observer8
Гость
« Ответ #190 : Март 02, 2014, 09:00 »

Igors, спасибо огромное! Исправлю ошибки. Всё таки есть ещё куда развивать этот проектик Улыбающийся

P.S. Я хочу чуть позже реализовать рисование в 3D. Мне кажется, что архитектура моего приложения несколько изменится. Как я понял в OpenGL все объекты состоят из треугольников и\или квадратов. Мои классы фигур будут хранить больше координат. Получается, что для круга мне нужно будет окружность задавать через координаты треугольников  В замешательстве
Записан
Igors
Джедай : наставник для всех
*******
Offline Offline

Сообщений: 11445


Просмотр профиля
« Ответ #191 : Март 02, 2014, 09:31 »

Всё таки есть ещё куда развивать этот проектик Улыбающийся
Поверьте, Вы его практически даже не начали  Улыбающийся

P.S. Я хочу чуть позже реализовать рисование в 3D. Мне кажется, что архитектура моего приложения несколько изменится. Как я понял в OpenGL все объекты состоят из треугольников и\или квадратов. Мои классы фигур будут хранить больше координат. Получается, что для круга мне нужно будет окружность задавать через координаты треугольников  В замешательстве
Ладно, поговорим об архитектуре. Вот у Вас Circle имеет radius. На первый взгляд это не вызывает сомнений, ну как же круг без радиуса? Это же его "неотъемлемое" свойство. Однако большой круг или маленький - все равно "круг", форма-то (shape) одна. Теперь более конкретно: каждый раз, создавая Circle мы создаем и массив координат для него, а в перспективе этих данных еще больше. Создал юзер напр 1000 объектов - и у нас 1000 массивов (вероятно совершенно одинаковых). А ведь легко сделать умнее: хранить один "эталонный" массив для радиуса = 1, и в момент рисования скалить его до нужного. Да, но тогда выходит сам shape еще недостаточен, нужен еще класс (вот он и будет хранить радиус), а какой? Впрочем у Вас и так shape недостаточен, позицию он не хранит, пока задаете от фонаря.

Вообще программист всегда хорошо знает чего он хочет от класса, что класс должен уметь и чего нет (последнее часто более важно). Записать это словами в файл - совсем не вредно. А Вы заболтили все проектирование и бегаете с какой-то бижутерией/аксессуарами  Улыбающийся
Записан
8Observer8
Гость
« Ответ #192 : Апрель 03, 2014, 13:42 »

Многие пишут, что это самая лучшая книга по ООП (объектно-ориентированному программированию и проектированию). Я только начал. Написано просто. Может кто-то ещё не читал и кому-то эта информация пригодится.

Приёмы объектно-ориентированного проектирования. Паттерны проектирования
Год: 2010
Автор: Гамма Э., Хелм Р., Джонсон Р., Влиссидес Дж.
Язык: Русский
Количество страниц: 366
Ссылка: http://rutracker.org/forum/viewtopic.php?t=3193196

Описание: В предлагаемой книге описываются простые и изящные решения типичных задач, возникающих в объектно-ориентированном проектировании. Паттерны появились потому, что многие разработчики искали пути повышения гибкости и степени повторного использования своих программ. Найденные решения воплощены в краткой и легко применимой на практике форме. Авторы излагают принципы использования паттернов проектирования и приводят их каталог. Таким образом, книга одновременно решает две задачи. Во-первых, здесь демонстрируется роль паттернов в создании архитектуры сложных систем. Во-вторых, применяя содержащиеся в справочнике паттерны, проектировщик сможет с легкостью разрабатывать собственные приложения.

Издание предназначено как для профессиональных разработчиков, так и для программистов, осваивающих объектно-ориентированное проектирование.
« Последнее редактирование: Апрель 03, 2014, 13:49 от 8Observer8 » Записан
Страниц: 1 ... 11 12 [13]   Вверх
  Печать  
 
Перейти в:  


Страница сгенерирована за 0.334 секунд. Запросов: 23.