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

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

Страниц: 1 [2] 3   Вниз
  Печать  
Автор Тема: Qt unhanded win32 exception  (Прочитано 15656 раз)
Majestio
Гость
« Ответ #15 : Май 15, 2013, 21:43 »

А теперь напишу как правильно делать) Только схожу выкурю сигару  Крутой
Записан
thechicho
Гость
« Ответ #16 : Май 15, 2013, 21:49 »

Dialog::~Dialog()
{
    delete ui;
    db.close();
}

а так
Записан
qwyllum
Гость
« Ответ #17 : Май 15, 2013, 21:52 »

Проверено электроникой!
Спасибо! Ваша программа работает без ошибок. Но в диалоге содержится объект QSqlDatabase, тогда как у меня это отдельный класс. В перспективе там будет куча методов обращения к БД.
Поэтому остался главный вопрос - что в моем коде не так? Эх, пойду заварю чай и продолжу копать)
Записан
qwyllum
Гость
« Ответ #18 : Май 15, 2013, 21:59 »

Dialog::~Dialog()
{
    delete ui;
    db.close();
}

а так
Спасибо! Реально, огромное спасибо) программа больше не выдает ошибок. Одно странно, я думал, что Qt должен сам завершать соединение при уничтожении переменной. Но век живи, век учись Улыбающийся
Записан
Majestio
Гость
« Ответ #19 : Май 15, 2013, 22:06 »

1) Из проекта убираете все неработающее, связанное с БД.

2) В проект добавляете это myglobal.h и myglobal.cpp

myglobal.h
Код:
#ifndef MYGLOBAL_H
#define MYGLOBAL_H

#include <QtGui>
#include <QtSql>

class MyGlobal {

public:
        QString  DbHost;
        QString  DbName;
        QString  DbUser;
        QString  DbPass;

    QSqlDatabase DataBase;

    MyGlobal();
    bool OpenDB();
};

#endif // MYGLOBAL_H

myglobal.cpp
Код:
#include "myglobal.h"

MyGlobal Global;

MyGlobal::MyGlobal()
{
}

bool MyGlobal::OpenDB()
{
    DataBase = QSqlDatabase::addDatabase("QPSQL","First");
    DataBase.setHostName(DbHost);
    DataBase.setDatabaseName(DbName);
    DataBase.setUserName(DbUser);
    DataBase.setPassword(DbPass);
    if (DataBase.open()) return true;
    return false;
}

3) Во всех модулях, где нужно обращение к БД прописываете #include "myglobal.h".

Это даст возможность обращаться с статическому экземпляру класса вот так:

Код:
Global.DbHost = "192.168.1.123";
Global.DbName = "mybase";
Global.DbUser = "im_super";
Global.DbPass = "secret";

if (!Global.OpenDB()) {
  qDebug() << "Shit happyness!";
}
...
Сделал урезанный вариант этого класса, у меня там все глобальные переменные приложения и еще куча методов для работы с транзакциями и блокировками.

Помните - обращение к этому всему делать строго из любого слота.
Чтобы соединение пошло автоматом после открытия диалога - слот по синглшоту вы уже знаете как вызывать.
« Последнее редактирование: Май 15, 2013, 22:09 от Majestio » Записан
thechicho
Гость
« Ответ #20 : Май 15, 2013, 22:10 »

чтобы Qt удалял, надо парента указывать.
при удалении парента, вызывается деструктор объекта.

DataBase db(this);

а в деструкторе уже

DataBase::~DataBase()
{
    body.close();
}

хотя я в теории не особо силен, поэтому не уверен, что сработает. попробуйте
Записан
Majestio
Гость
« Ответ #21 : Май 15, 2013, 22:31 »

А вообще в духе расовой чистоты считаю что QSqlDatabase обязательно нужно выносить в глобальную статическую переменную. Это даст:

1) возможность обращения к "хэндлу" БД из любого виджета приложения
2) мотивацию не заниматься созданиями/уничтожениями "хэндлов" БД без очевидной необходимости
3) возможность управления множеством БД (если такое требуется) из любого виджета приложения

Правда в таком случае нужно подпилить напильником типа этого:

QMap <QString, QSqlDatabase*> MyClaster;

Вот тогда имеет смысл динамически управлять экземплярами QSqlDatabase.
« Последнее редактирование: Май 15, 2013, 22:33 от Majestio » Записан
thechicho
Гость
« Ответ #22 : Май 15, 2013, 22:45 »

//QSqlDatabase обязательно нужно выносить в глобальную статическую переменную

имеется в виду этот объект? MyGlobal Global;
почему он статический?

по поводу глобального класса для доступа к бд, хз.
у тс отдельный класс для работы с бд. создает объект бд, когда надо. так удобнее по идее.
хотя мой опыт работы с бд заканчивается на единичном подключении к бд стандартными методами кьют, без вспомогательных классов.
Записан
Old
Джедай : наставник для всех
*******
Online Online

Сообщений: 4350



Просмотр профиля
« Ответ #23 : Май 15, 2013, 23:00 »

А вообще в духе расовой чистоты считаю что QSqlDatabase обязательно нужно выносить в глобальную статическую переменную. Это даст:
Да почитайте вы уже документацию по этому классу. Улыбающийся
Не нужно ничего никуда выносить. Он сам предоставляет кучу методов для доступа к соединению из любого места программы.
Записан
Majestio
Гость
« Ответ #24 : Май 15, 2013, 23:09 »

имеется в виду этот объект? MyGlobal Global;
почему он статический?

Статические экземпляры класса создаются сразу же после старта приложения (не дожидаясь, к примеру создания экземпляра главного окна). Это гарантирует то, что к моменту создания любого виджета есть набор общих переменных, видимость которых должна быть глобальной.

по поводу глобального класса для доступа к бд, хз.
у тс отдельный класс для работы с бд. создает объект бд, когда надо. так удобнее по идее.

Представим сценарий многопользовательской работы с БД.

1) С "моим" подходом - подключился к БД в начале "сеанса" работы, отключился в конце. Как минимум это дает возможность "спросить" БД, а сколько и кто именно сейчас в онлайне.
2) С динамическими подключениями, отключениями ... а смысл создавать и уничтожать "хэндлы"? На это же уходит  дополнительное время, как минимум.
3) С неглобальным хранением "хэндлов" БД ... а кому отдать владение? И главное зачем его потом делать глобально видимым ... а еще не забыть его проинициализировать вовремя...

Ну вот как-то так.

ЗЫ: Сейчас я свое приложение оформляю в виде DLL с отложенной загрузкой. В dll-ке вообще несколько "главных" окон (инициализируемых интерфейсов), кто из них главнее?  Показает язык
Записан
Majestio
Гость
« Ответ #25 : Май 15, 2013, 23:14 »

Да почитайте вы уже документацию по этому классу. Улыбающийся
Не нужно ничего никуда выносить. Он сам предоставляет кучу методов для доступа к соединению из любого места программы.

Милейший, у меня приложение поднимает два соединения. Одно работает с транзакциями и блокировками. Второе - регистрирует операции в базе (кто залочил, когда, кто удалил, и пр ...). Второе нужно для того, чтобы эти операции можно было проводить во время открытой и еще незавершенной транзакции (первого соединения). Поэтому я остаюсь при свое точке зрения, со всем уважением  Подмигивающий
Записан
Old
Джедай : наставник для всех
*******
Online Online

Сообщений: 4350



Просмотр профиля
« Ответ #26 : Май 15, 2013, 23:20 »

Милейший, у меня приложение поднимает два соединения. Одно работает с транзакциями и блокировками. Второе - регистрирует операции в базе (кто залочил, когда, кто удалил, и пр ...). Второе нужно для того, чтобы эти операции можно было проводить во время открытой и еще незавершенной транзакции (первого соединения). Поэтому я остаюсь при свое точке зрения, со всем уважением  Подмигивающий
Это нужно исключительно вам исключительно для этого приложения, не находите?
Так почему вы рекомендуете это для всех и всегда? В большинстве случаев это избыточно и хватает функционала предоставляемого самим QSqlDatabase.

А про статические объекты/переменные не писал только ленивый. Чем меньше их будет у вас программе, тем проще ее будет сопровождать в дальнейшем.
Записан
Majestio
Гость
« Ответ #27 : Май 15, 2013, 23:34 »

Это нужно исключительно вам исключительно для этого приложения, не находите?
Так почему вы рекомендуете это для всех и всегда? В большинстве случаев это избыточно и хватает функционала предоставляемого самим QSqlDatabase.

1) Ваш вариант - QSqlDatabase::database("MyDB")
2) Мой вариант - Global.MyDB

Я, как минимум, экономлю электричество на написание лишних на 19 символов, как максимум - на отсутствии необходимости Qt бессмысленного поиска "MyDB" в списке зарегистрированных соединений.

А про статические объекты/переменные не писал только ленивый. Чем меньше их будет у вас программе, тем проще ее будет сопровождать в дальнейшем.

Мало ли кто чего писал  Смеющийся ... Лично у меня только одна - MyGlobal. И в ней все глобальной видимости. Не понимаю, зачем изобретать овальные колеса - если круглое и так ниче.
Записан
Old
Джедай : наставник для всех
*******
Online Online

Сообщений: 4350



Просмотр профиля
« Ответ #28 : Май 15, 2013, 23:36 »

Не понимаю, зачем изобретать овальные колеса - если круглое и так ниче.
А это дело времени и масштаба проекта... Поймете. Подмигивающий
Записан
thechicho
Гость
« Ответ #29 : Май 15, 2013, 23:37 »

//Статические экземпляры класса создаются сразу же после старта приложения (не дожидаясь, к примеру создания экземпляра главного окна). Это гарантирует то, что к моменту создания любого виджета есть набор общих переменных, видимость которых должна быть глобальной.

может под статической переменной вы имеете в виду переменную, созданную в стеке?
согласно http://ru.wikipedia.org/wiki/%D0%A1%D1%82%D0%B0%D1%82%D0%B8%D1%87%D0%B5%D1%81%D0%BA%D0%B8%D0%B9_%D0%BA%D0%BB%D0%B0%D1%81%D1%81

переменную (объект класса) MyGlobal Global; нельзя назвать статической, т.к. не каждая функция класса статическая (их вообще нет).

то есть глобальная переменная - да
глобальная статическая переменная - нет

или я что-то не так понимаю? если не трудно, скиньте ссылку, где вы прочитали, что статические экземпляры класса создаются сразу же после старта приложения
Записан
Страниц: 1 [2] 3   Вверх
  Печать  
 
Перейти в:  


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