Russian Qt Forum

Qt => Вопросы новичков => Тема начата: andrew.k от Апрель 08, 2015, 12:00



Название: Почему падает тестовое приложение
Отправлено: andrew.k от Апрель 08, 2015, 12:00
Если в TestApp раскомментировать два qDebug(), то все работает как положено.

Код приложения:

Код
C++ (Qt)
// main.cpp
#include "testapp.h"
#include <QApplication>
#include <QtDebug>
#include <QTimer>
 
int main(int argc, char *argv[])
{
//      new QApplication(argc, argv);
       TestApp ta(argc, argv);
 
       QTimer::singleShot(1000, qApp, SLOT(quit()));
       return qApp->exec();
}
 
 

Код
C++ (Qt)
// testapp.h
#include <QObject>
 
class TestApp : public QObject
{
       Q_OBJECT
 
public:
       TestApp(int argc, char * argv[], QObject * parent = 0);
       ~TestApp();
 
private:
       static TestApp * instance_;
};
 
 

Код
C++ (Qt)
// testapp.cpp
#include "testapp.h"
#include <QApplication>
#include <QtDebug>
 
TestApp * TestApp::instance_ = 0;
 
TestApp::TestApp(int argc, char * argv[], QObject *parent)
       :QObject(parent)
{
//      qDebug() << "TestApp::TestApp()";
       instance_ = this;
       new QApplication(argc, argv);
}
 
TestApp::~TestApp()
{
//    qDebug() << "TestApp::~TestApp()";
   delete qApp;
}
 
 


Название: Re: Почему падает тестовое приложение
Отправлено: __Heaven__ от Апрель 08, 2015, 12:07
У меня отработало без вылета.
Win7x64 qt5.4.1 mingw


Название: Re: Почему падает тестовое приложение
Отправлено: Пантер от Апрель 08, 2015, 12:14
Бггггг. :D
А теперь внимательно присмотрись к тому, как QCoreApplication принимает argc.


Название: Re: Почему падает тестовое приложение
Отправлено: Пантер от Апрель 08, 2015, 12:15
Да, синглтон у тебя херовый.


Название: Re: Почему падает тестовое приложение
Отправлено: __Heaven__ от Апрель 08, 2015, 12:23
После отработки конструктора TestApp происходит артефакт, отгадал?


Название: Re: Почему падает тестовое приложение
Отправлено: andrew.k от Апрель 08, 2015, 12:23
У меня отработало без вылета.
Win7x64 qt5.4.1 mingw
в qt4.8 у меня тоже без вылета отработало.


Название: Re: Почему падает тестовое приложение
Отправлено: andrew.k от Апрель 08, 2015, 12:25
Бггггг. :D
А теперь внимательно присмотрись к тому, как QCoreApplication принимает argc.
Жесть! В жизни б не догадался) Никогда не обращал на это внимание.
Зачем так сделали, не понятно.

Спасибо!


Название: Re: Почему падает тестовое приложение
Отправлено: Пантер от Апрель 08, 2015, 12:25
Когда-то я такую проблему отхватил через 4 года существования проекта (переданного мне). То есть, 4 года все работало и внезапно стало падать. Причем, только у меня. Так сошлись звезды, версия компилятора и что-то там еще.


Название: Re: Почему падает тестовое приложение
Отправлено: andrew.k от Апрель 08, 2015, 12:26
Да, синглтон у тебя херовый.
Чем он плох?


Название: Re: Почему падает тестовое приложение
Отправлено: Пантер от Апрель 08, 2015, 12:27
Бггггг. :D
А теперь внимательно присмотрись к тому, как QCoreApplication принимает argc.
Жесть! В жизни б не догадался) Никогда не обращал на это внимание.
Зачем так сделали, не понятно.

Спасибо!
Кьют может удалять из входных параметров определенные вещи (допустим, -style style_name).


Название: Re: Почему падает тестовое приложение
Отправлено: Пантер от Апрель 08, 2015, 12:28
Да, синглтон у тебя херовый.
Чем он плох?
Тем, что он не синглтон. Кто будет проверять на то, что инстанс ненулевой?


Название: Re: Почему падает тестовое приложение
Отправлено: __Heaven__ от Апрель 08, 2015, 12:32
А для чего такие синглтоны служат? Никогда не применял


Название: Re: Почему падает тестовое приложение
Отправлено: andrew.k от Апрель 08, 2015, 12:34
Да, синглтон у тебя херовый.
Чем он плох?
Тем, что он не синглтон. Кто будет проверять на то, что инстанс ненулевой?
Да это я так сделал для теста.
можно добавить Q_ASSERT(instance_ == nullptr) :)

Так то его вообще нельзя назвать синглтоном, нет функции возвращающей экземпляр)


Название: Re: Почему падает тестовое приложение
Отправлено: andrew.k от Апрель 08, 2015, 12:35
А для чего такие синглтоны служат? Никогда не применял
Например, QCoreApplication типичный пример синглтона.


Название: Re: Почему падает тестовое приложение
Отправлено: Пантер от Апрель 08, 2015, 12:37
В синглтонах конструктор делают приватным и работают через SingletonClassName::instance()->someMethod().


Название: Re: Почему падает тестовое приложение
Отправлено: Igors от Апрель 08, 2015, 13:00
Только вчера за это тоже получил получил по дюнделю :) Как они сами объясняют - потому что число аргументов может меняться. Да, может, напр я зарядил имя файла (одного) в командной строке. На старте в командной строке получаю ... 4 параметра.

1) Полное имя приложения
2) Имя файла что я дал
3) Какая-то лабуда типа -хххDebug
4) "YES"

Когда запустился цикл событий мне пришло событие QEvent::OpenFile и теперь остался 1 аргумент. Хммм... ну ладно, а  как мне самому, "до того" убрать/отфильтровать весь этот хлам из командной строки?


Название: Re: Почему падает тестовое приложение
Отправлено: andrew.k от Апрель 08, 2015, 14:33
Только вчера за это тоже получил получил по дюнделю :) Как они сами объясняют - потому что число аргументов может меняться. Да, может, напр я зарядил имя файла (одного) в командной строке. На старте в командной строке получаю ... 4 параметра.

1) Полное имя приложения
2) Имя файла что я дал
3) Какая-то лабуда типа -хххDebug
4) "YES"

Когда запустился цикл событий мне пришло событие QEvent::OpenFile и теперь остался 1 аргумент. Хммм... ну ладно, а  как мне самому, "до того" убрать/отфильтровать весь этот хлам из командной строки?

Ну так видимо, до того, как до него доберется Qt. До создания QApplication.


Название: Re: Почему падает тестовое приложение
Отправлено: Igors от Апрель 08, 2015, 14:46
Ну так видимо, до того, как до него доберется Qt. До создания QApplication.
Когда QApplication создано - мусор в командной строке еще торчит, И когда, по каким правилам оно его вычищает - хз


Название: Re: Почему падает тестовое приложение
Отправлено: andrew.k от Апрель 08, 2015, 14:46
В синглтонах конструктор делают приватным и работают через SingletonClassName::instance()->someMethod().
QApplication тоже синглтон, но конструктор там не приватный.


Название: Re: Почему падает тестовое приложение
Отправлено: andrew.k от Апрель 08, 2015, 15:00
Ну так видимо, до того, как до него доберется Qt. До создания QApplication.
Когда QApplication создано - мусор в командной строке еще торчит, И когда, по каким правилам оно его вычищает - хз
Судя по исходникам, аргументы удаляются в конструкторе QApplication

Код
C++ (Qt)
void QApplicationPrivate::process_cmdline()
{
   // process platform-indep command line
   if (!qt_is_gui_used || !argc)
       return;
 
   int i, j;
 
   j = 1;
   for (i=1; i<argc; i++) { // if you add anything here, modify QCoreApplication::arguments()
       if (argv[i] && *argv[i] != '-') {
           argv[j++] = argv[i];
           continue;
       }
       QByteArray arg = argv[i];
       if (arg.startsWith("--"))
           arg.remove(0, 1);
       QString s;
       if (arg == "-qdevel" || arg == "-qdebug") {
           // obsolete argument
       } else if (arg.indexOf("-style=", 0) != -1) {
           s = QString::fromLocal8Bit(arg.right(arg.length() - 7).toLower());
       } else if (arg == "-style" && i < argc-1) {
           s = QString::fromLocal8Bit(argv[++i]).toLower();
#ifndef QT_NO_STYLE_STYLESHEET
       } else if (arg == "-stylesheet" && i < argc -1) {
           styleSheet = QLatin1String("file:///");
           styleSheet.append(QString::fromLocal8Bit(argv[++i]));
       } else if (arg.indexOf("-stylesheet=") != -1) {
           styleSheet = QLatin1String("file:///");
           styleSheet.append(QString::fromLocal8Bit(arg.right(arg.length() - 12)));
#endif
       } else if (qstrcmp(arg, "-widgetcount") == 0) {
           widgetCount = true;
       } else {
           argv[j++] = argv[i];
       }
       if (!s.isEmpty()) {
           if (app_style) {
               delete app_style;
               app_style = 0;
           }
           styleOverride = s;
       }
   }
 
   if(j < argc) {
       argv[j] = 0;
       argc = j;
   }
}
 


Код
C++ (Qt)
void QApplicationPrivate::construct()
{
   initResources();
 
   qt_is_gui_used = (application_type != QApplicationPrivate::Tty);
   process_cmdline();
....
 

Код
C++ (Qt)
#ifdef Q_QDOC
QApplication::QApplication(int &argc, char **argv)
#else
QApplication::QApplication(int &argc, char **argv, int _internal)
#endif
   : QGuiApplication(*new QApplicationPrivate(argc, argv, _internal))
{ Q_D(QApplication); d->construct(); }
 

Эксперимент это подтверждает. -style test.qss исчез из аргументов, после создания экземпляра QApplication, до запуска очереди событий.


Название: Re: Почему падает тестовое приложение
Отправлено: Igors от Апрель 09, 2015, 08:24
Эксперимент это подтверждает. -style test.qss исчез из аргументов, после создания экземпляра QApplication, до запуска очереди событий.
А у меня не подтверждает - печатаю qApp->arguments из своего констуктора, стало быть конструктор QApplication уже отработал.


Название: Re: Почему падает тестовое приложение
Отправлено: andrew.k от Апрель 09, 2015, 15:31
Эксперимент это подтверждает. -style test.qss исчез из аргументов, после создания экземпляра QApplication, до запуска очереди событий.
А у меня не подтверждает - печатаю qApp->arguments из своего констуктора, стало быть конструктор QApplication уже отработал.
Возможно "Ты просто не умеешь их готовить" (с) :)
Qt 5.2.1 Ubuntu

Код:
Код
C++ (Qt)
#include <iostream>
#include <QApplication>
#include <QtDebug>
 
void printArgs(int argc, char *argv[])
{
       std::cout << "argc = " << argc << std::endl;
       for(int i = 0; i < argc; ++i)
               std::cout << "argv[" << i << "]=" << argv[i] << std::endl;
       std::cout << std::endl;
}
 
int main(int argc, char *argv[])
{
       printArgs(argc, argv);
       QApplication a(argc, argv);
       printArgs(argc, argv);
       qDebug() << a.arguments();
       return 0;
}
 

Вывод:
Код
Bash
andrew@fastback:~/projects/testargs$ ./testargs -style test.qss
argc = 3
argv[0]=./testargs
argv[1]=-style
argv[2]=test.qss
 
argc = 1
argv[0]=./testargs
 
("./testargs")