Qt interview guide (including interview questions)

Qt interview guide (including interview questions)

What skills are required for QT development positions?

QT development positions require mastering skills such as C++ language, QT framework, GUI programming, and multi-threaded programming. In addition, different positions also require knowledge in different fields, such as network programming, database programming, etc.

How to prepare for QT interview?

First of all, you need to understand the company's recruitment requirements and job responsibilities, as well as the interview process and interview format. Secondly, you need to prepare the knowledge and skills required for the interview, which can be done by reading relevant books, attending training courses, doing practice questions, etc. Finally, you need to conduct a mock interview to find your own shortcomings and improve them.

Benefits of this article, receive free Qt development learning materials package and technical videos, including (Qt practical project video tutorial + code, C++ Language foundation, C++ design pattern, introduction to Qt programming, QT signal and slot mechanism, QT interface development-image drawing, QT network, QT database programming, QT project practice, QSS, OpenCV, Quick module, interview questions, etc.) ↓↓↓ ↓↓↓See below↓↓Click at the bottom of the article to receive the fee↓↓

Interview questions: (If you need a pdf document, you can go to Penguin 937552610 skirt)

1. Basic knowledge of c++

1. Synchronization method of processes and threads

Process: 1) Pipe, which is a series of caches in the kernel

2) Message queue

3) Shared memory

4) Semaphore mechanism

5) Signal

6)socket

Thread: 1) Waiting for notification mechanism

2) Shared memory

3) Pipeline

5) Concurrency tools

Semaphore, read-write lock, mutex lock and condition variable

The deadlock concept of threads: threads wait for each other for critical resources, causing each other to be unable to continue executing.

method one

1) Create a sub-object of the thread class and inherit QThread:

2) Rewrite the run() method of the parent class, and write the specific business process to be processed by the child thread inside this function

3) Create a sub-thread object in the main thread, new one

4) Start the child thread and call the start() method

Method 2

1) Create a new class, derived from QObject

2) Add a public custom member function to the class. The function body is the business logic executed in the child thread.

3) Create a QThread object in the main thread, which is the child thread object

4) Create a working class object in the main thread and do not specify a parent object for the created object.

5) To move the Mywork object to the created sub-thread object, you need to call the moveToThread() method provided by the QObject class

Precautions:

Business object, the parent object cannot be specified when constructing

UI windows (UI-related classes) cannot be processed in child threads

Only some data-related operations can be processed in the child thread, and windows cannot be involved.

2. What is a stack?

stack

Heap abstract data structure: last in, first out

Global area (static area) (static)

Literal constant area

Program code area

The stack is automatically allocated and released, a first-level cache, and an array-like structure.

The heap is allocated and released by the programmer, and the second-level cache is slower, first in, last out.

3. Commonly used sorting

Insertion sort, Hill sort, selection sort, bubble sort, heap sort, quick sort

Bubble Sort:

Time complexity: O(n) at best, O(n to the power of 2) at worst.

Space complexity: O(1);

4. The difference between arrays and linked lists

1) The array is continuously stored, has a fixed length, and adding or deleting requires moving other elements. The linked list is dynamically allocated, not continuous, and requires malloc or

new applies for memory, free or delete when not in use.

2) Array access efficiency is high, and linked list deletion and insertion efficiency is high

3) The array is positioned using subscripts, and the time complexity of the search is O(1). The linked list locates elements by traversing, and the time complexity of the search is O(N).

4) Array insertion and deletion require moving other elements, and the time complexity is O(N). Insertion or deletion of linked lists does not require moving other elements, and the time complexity is O(1).

5. Three typical usage scenarios of callback functions:

1) Implement function redefinition

2) Extended function functions

3) Implement program hierarchical design

6. Distinguish between static and const

static :

(1) Modify global variables: Variables are only visible within this module. When defining global variables that do not need to be shared with other files, adding the static keyword can effectively reduce the coupling between program modules and avoid variables with the same name in different files. conflicts and cannot be misused.

(2) Modify local variables: The variable allocates memory space in the global data area, and the compiler automatically initializes it. Its scope is the local scope. When the function that defines it ends, its scope ends.

(3) Modified functions: Functions are used in a similar way to global variables. Adding static before the return type of the function is a static function. A static function can only be visible in the file in which it is declared. Other files cannot reference the function. Different Files can use static functions with the same name without affecting each other.

const :

Variables modified by const are read-only variables, which are still variables in nature. Some people call them constant variables. The difference from ordinary variables is that constant variables cannot be used for lvalues. The rest of the usage is the same as ordinary constants, and the variable name cannot be changed.

7. Have you ever used dynamic libraries and static libraries at work? Can you briefly explain the difference between the two?

Answer: Static library: During the linking phase, the target file .o generated by assembly is linked and packaged into an executable file together with the reference library, which can be simply regarded as (a collection of .o or .obj files). (1) Linking to the function library is completed during compilation (2) The program has nothing to do with the function library at runtime, making it easy to transplant (3) A waste of space and resources

Dynamic library: (1) Delays the link loading of library functions until the program is running (2) It can realize resource sharing between processes (so it is also called a shared library) (3) It makes it easy to upgrade some programs (4) It can The real link loading is completely controlled by the programmer in the program code (explicit call)

8. Virtual function:

A pointer to a parent type points to an instance of its child class

Classes with virtual functions have a one-dimensional virtual function table called a virtual table.

Objects of a class have a virtual pointer pointing to the beginning of the virtual table. The virtual table corresponds to the class, and the virtual table pointer corresponds to the object.

Default constructor, initializing constructor, copy constructor, move constructor

Why can't a constructor be declared as a virtual function?

The virtual function corresponds to a vtale, and the address of this table is stored in the memory space of the object. If you set the constructor to virtual,

You need to call it in the vtable, but the object has not been instantiated and there is no memory space allocated. How to call it?

9. STL related knowledge

STL consists of 6 parts: Container, Algorithm, Iterator,

Function object, Adaptor, Allocator

Containers, algorithms, iterators, functors, adapters, space configurators

Container: array, linked list, tree, stack, queue, set, map

string container

Vector container is a continuous memory space with one-way opening, while deque is a continuous linear space with two-way opening.

stack is a first in last out

Queue is a first-in-first-out

The list container linked list is a non-continuous and non-sequential storage structure on a physical storage unit.

set/multiset binary tree

map/multimap binary tree

Swap, search, traverse, copy, modify, reverse, sort, merge, etc.

10. Smart pointers: auto_ptr (abandoned after 17), unique_ptr, shared_ptr and weak_ptr

The essence of a smart pointer is a class template. When the smart pointer object is used up, the object will automatically call the destructor to release the space pointed by the pointer.

shared_ptr uses the reference counting principle to realize resource sharing between multiple shared_ptr objects:

shared_ptr internally maintains a reference count to record that the resource is shared by several objects.

When a shared_ptr object is destroyed (the destructor is called), the count is decremented by 1 in the destructor.

If the reference count decreases to 0, it means that you are the last shared_ptr object to use the resource and must release the resource.

If the reference count is not 0, it means that there are other objects in use, and the resource cannot be released, otherwise the other objects will become wild pointers.

11. The difference between pointers and references

A pointer is an entity, while a reference is just an alias.

A reference can only be initialized once when it is defined and is immutable thereafter, but a pointer can change.

Pointers can have multiple levels, but references have only one level.

References cannot be null, pointers can be null.

"sizeof reference" gets the size of the variable (object) pointed to, while "sizeof pointer" gets the size of the pointer itself

The increment (++) operation of pointers and references has different meanings

References are type-safe, but pointers are not. References have more type checks than pointers.

References do not have const, pointers have const, and const pointers are immutable.

The way to access entities is different. The pointer needs to be explicitly dereferenced, and the reference compiler handles it by itself.

2. Network programming

1. Describe QT’s TCP communication process

Server: (QTcpServer)

①Create QTcpServer object

②The parameters required for the listening list are address and port number

③When a new client connects successfully, the newConnect signal is sent back

④In the newConnection signal slot function, call the nextPendingConnection function to obtain the new connection QTcpSocket object

⑤Connect the readRead signal of the QTcpSocket object

⑥Use read to receive data in the slot function of readRead signal

⑦Call the write member function to send data

Client: (QTcpSocket)

①Create QTcpSocket object

②When the object is successfully connected to the Server, the connected signal will be sent.

③Call the member function connectToHost to connect to the server. The required parameters are the address and port number.

④The slot function of the connected signal starts sending data

⑤Use write to send data and read to receive data.

1) Keep-alive problem of long connection

The standard TCP layer protocol sets the other party's timeout to 2 hours. If the server has not received the client's information for more than 2 hours, it will send a detection segment. If 10 detection segments are sent (each one is 75S apart) If no response is received, it is assumed that the client has failed and the connection is terminated. Therefore, long tcp connections should be kept alive.

2) TCP provides the push operation instruction that forces data to be transmitted immediately. After receiving the operation instruction, the TCP software immediately sends the data of this segment without waiting for the sending buffer to be full;

Solution 2: Send fixed-length messages

Solution 3: Send the message size together with the message

Solution 4: Both parties agree on the size of each transmission

Solution 5: Both parties agree to use special markers to distinguish message intervals

Solution 6: Standard protocols are processed according to protocol rules, such as Sip protocol

3) Sticky bag problem

The main reason for TCP's sticky packet problem is that TCP is connection-oriented, so in TCP's view, messages are not viewed as individual messages, but all messages are viewed as byte streams in TCP's view.

Therefore, when A and B messages are mixed together, TCP cannot distinguish them.

The most essential reason for the sticky problem is that the receiving peer cannot distinguish the boundaries between messages. We give bounds by using some scheme, for example:

Baotou plus body length. The packet header is a fixed length of 4 bytes, indicating the length of the packet body. The receiving pair first receives the packet body length, and then receives the packet body based on the packet body length.

Solution 1: TCP provides the push operation instruction that forces data to be transmitted immediately. After receiving the operation instruction, the TCP software immediately sends this data out without waiting for the sending buffer to be full;

Solution 2: Send fixed-length messages

Solution 3: Send the message size together with the message

Solution 4: Both parties agree on the size of each transmission

Solution 5: Both parties agree to use special markers to distinguish message intervals

Solution 6: Standard protocols are processed according to protocol rules, such as Sip protocol

The sending end adds a packet header to each data packet. The header should at least contain the length of the data packet. In this way, after receiving the data, the receiving end will know the actual length of each data packet by reading the length field of the packet header.

The sending end encapsulates each data packet into a fixed length (if it is not enough, it can be filled with 0s), so that the receiving end will naturally split each data packet every time it reads fixed-length data from the receiving buffer.

Boundaries can be set between data packets, such as adding special symbols, so that the receiving end can separate different data packets through this boundary.

Solution to specifying data length, main ideas:

We have a member in the data structure that represents the length (message header). We prepare a large enough message buffer (1024000 bytes in the program), and loop through recv in the socket to read up to 102400 bytes each time. , and then splice the messages received in the loop into the message buffer, until the received message is greater than the length indicated by the message header, then a complete message is received (so our message buffer must be larger than the complete message) ) for message processing.

4) Summary of the differences between TCP and UDP:

1. TCP is connection-oriented (such as making a phone call, you must first dial to establish a connection); UDP is connectionless, that is, there is no need to establish a connection before sending data.

2. TCP provides reliable services. That is to say, the data transmitted through the TCP connection is error-free, not lost, not repeated, and arrives in order; UDP uses its best efforts to deliver, that is, reliable delivery is not guaranteed.

3. TCP is byte stream oriented. In fact, TCP treats data as a series of unstructured byte streams; UDP is message oriented.

UDP has no congestion control, so network congestion will not reduce the source host's sending rate (useful for real-time applications, such as IP telephony, real-time video conferencing, etc.)

4. Each TCP connection can only be point-to-point; UDP supports one-to-one, one-to-many, many-to-one and many-to-many interactive communications.

5. TCP header overhead is 20 bytes; UDP header overhead is small, only 8 bytes

6. TCP’s logical communication channel is a full-duplex reliable channel, while UDP is an unreliable channel.

7. The specific process of three-way handshake and four-way wave

SYN: request to establish a connection, FIN: request to disconnect, ACK: confirm whether it is valid, seq: sequence number, ack: confirmation number

1) Three handshakes

1. The client sends a SYN=1 (requesting to establish a connection) to the server and generates a sequence number seq=j.

2. After receiving SYN=1, the server sends a SYN=1 and ACK=1 to the client; sets ack to j+1; and generates a sequence number seq=k.

3. When the client receives it, it will check whether the ack is j+1 and whether the ACK is 1. If so, it will send an ACK=1 and ack=k+1 to the server, as well as its own sequence number seq=j=1. ; When the server receives it, it will check whether the ACK is 1 and whether the ack is k+1. If so, it means that the connection is successfully established and data can be transferred between the two.

2) Wave four times

1. The client sends FIN=1 (requesting to close the connection) to the server and generates a sequence number seq=x.

2. After receiving the FIN, the server sends ACK=1, ack=x+1 to the client, and generates the sequence number seq=y (the client has no data to send, but the server needs to send the last data).

3. After the server has processed all the data, it sends FIN=1 and ACK=1, ack=x+1 to the client, and generates the sequence number z, indicating that the server can now disconnect.

4. After receiving the data packet from the server, the client will send ACK=1, seq=x=1, ack=z+1 to the server (it needs to wait 2MSL before disconnecting).

8. The difference between pointers and references

A pointer is an entity, while a reference is just an alias.

A reference can only be initialized once when it is defined and is immutable thereafter, but a pointer can change.

Pointers can have multiple levels, but references have only one level.

References cannot be null, pointers can be null.

"sizeof reference" gets the size of the variable (object) pointed to, while "sizeof pointer" gets the size of the pointer itself

The increment (++) operation of pointers and references has different meanings

References are type-safe, but pointers are not. References have more type checks than pointers.

References do not have const, pointers have const, and const pointers are immutable.

The way to access entities is different. The pointer needs to be explicitly dereferenced, and the reference compiler handles it by itself.

9. HTTP is a hypertext transfer protocol

The Internet protocol stack consists of five parts: physical layer, link layer, network layer, transport layer and application layer

URL

The browser will provide the URL to DNS (domain name server, which will be discussed later)

HTML is called Hypertext Markup Language

The http protocol is an application layer protocol, which mainly solves how to package data. The tcp protocol is a transport layer protocol, which mainly solves how data is transmitted in the network.

In layman's terms, the task of HTTP is to exchange information with the server. It does not matter how it connects to the server and ensures that the data is correct. The task of tcp is to ensure the reliability of the connection. It only cares about the connection and does not care about the data to be transmitted after the connection.

The http protocol is built on top of tcp. http is a stateless short link, while tcp is a stateful long link.

HTTPS: It is an HTTP channel aimed at security and is a secure version of HTTP. The security foundation of HTTPS is SSL.

The SSL protocol is located between the TCP/IP protocol and various application layer protocols, providing security support for data communication.

2. The difference between HTTP and HTTPS

1. The HTTPS protocol requires applying for a certificate from a CA (Certificate Authority). Generally, there are fewer free certificates, so a certain fee is required.

(The previous NetEase official website was http, and the NetEase email address was https.)

2. HTTP is Hypertext Transfer Protocol, information is transmitted in plain text, while HTTPS is a secure SSL encrypted transmission protocol.

3. HTTP and HTTPS use completely different connection methods and use different ports. The former is 80 and the latter is 443.

4. HTTP connection is very simple and stateless. The HTTPS protocol is a network protocol built from the SSL+HTTP protocol that can perform encrypted transmission and identity authentication.

More secure than HTTP protocol. (Stateless means that the sending, transmission and reception of data packets are independent of each other.

Connectionless means that neither party in the communication can maintain any information about the other party for a long time. )

3. QT related knowledge

1. What is a meta-object system?

The meta-object system is an extension based on standard C++, which provides QT with signal and slot mechanisms, real-time type information, and dynamic property systems.

There are three basic conditions for the meta-object system: the class must inherit from QObject, the class declares the Q_OBJECT macro (default private), and the meta-object compiler moc.

Signals and slots are similar to the observer pattern;

The essence of the callback function is based on "you want other people's code to execute your code, but you cannot touch other people's code";

object tree;

The implementation of signals and slots relies on Qt's meta-object system. The meta-object system has a meta-object compiler.

There will be a preprocessing process before the program is compiled. The preprocessing will save the string values ​​of signals and slots in a class/object in a container, which may be a string or other ordered container.

The fifth parameter is related to thread Qt::AutoConnection

1) Advantages of Qt signal and slot mechanism

(1) Type safety. The signatures of the signals and slots that need to be associated must be identical.

(2) Loose coupling.

(3) The signal and slot mechanism enhances the flexibility of communication between objects. A signal can be associated with multiple slots, and multiple signals can be associated with one slot.

2) Shortcomings of Qt’s signal and slot mechanism

Compared to callback functions, the signals and slots mechanism is somewhat slow. Calling a slot function by passing a signal will run 10 times slower than calling a non-virtual function directly. Here’s why:

(1) It is necessary to locate the object receiving the signal;

(2) Safely traverse all associations (such as a signal associated with multiple slots);

(3) Group/unmarshal the passed parameters;

(4) When using multiple threads, signals may need to be queued.

However, compared to the new operation that creates an object and the delete operation that deletes an object, the running cost of signals and slots is only a small part of them. This performance loss caused by the signal and slot mechanism is negligible for real-time applications.

Do you know how many levels of event filtering the QT event mechanism has? Can you give a rough description?

Answer: Based on the analysis of Qt event mechanism, we can get 5 levels of event filtering and processing methods. The functions are arranged from weak to strong as follows:

1) Overload specific event handling functions.

The most common event handling method is to overload specific event handling functions such as mousePressEvent(), keyPressEvent(), paintEvent().

2) Overload the event() function.

By overloading the event() function, we can handle the event before it is handled by a specific event handler (such as keyPressEvent()). For example, when we want to change the default action of the tab key, we generally need to override this function. evnet() is also useful when handling some uncommon events (such as LayoutDirectionChange), because these functions do not have corresponding specific event handling functions. When we overload the event() function, we need to call the event() function of the parent class To handle events that we don’t need to handle or don’t know how to handle.

3) Install event filters on Qt objects.

There are two steps to install an event filter: (Suppose you want to use A to monitor and filter events of B)

First call B's installEventFilter( const QOject *obj), taking A's pointer as a parameter. In this way, all events sent to B will first be processed by A's eventFilter().

Then, A needs to overload the QObject::eventFilter() function and write the code to process the event in eventFilter().

4) Install event filters for the QApplication object.

Once we install a filter on qApp (the only QApplication object in each program), all events must first pass through the current eventFilter() before being sent to any other filter. When debugging, this method It is very useful and is often used to handle mouse events of invalid widgets. Usually these events will be discarded by QApplication::notify(). (In QApplication::notify(), the filter of qApp is called first, and then Events are analyzed to decide whether to merge or discard)

5) Inherit the QApplication class and overload the notify() function.

Qt uses the QApplication::notify() function to distribute events. If you want to get these events before any event filter looks at any event, overloading this function is the only way. Generally speaking, event filters are better to use , because there is no need to inherit the QApplication class. And any number of events can be installed on the QApplication object.

Custom interface

The UI designer integrates the editing functions of Qt style sheets

foreground color

background-color background-color

Color after selection selection-color

background-image background-image

Selector: QPushButton, QDialog QPushButton, QPushButton#btnOk

Child items: drop-down, up-button, down-button

Pseudo state: hover (when the mouse moves over the item), active (in the active form)

Attributes: min_width, padding-top, border-width,

1. Use Qt Designer

2、qApp->setStyleSheet(“QLineEdit{ background-color: gray}”);

Custom QT control

1. Customize Widget subclass QmyBattery

paintEvent() event

QmyBattery inherits from QWidget

Q_UNUSED(event)

QPainter/QRect/QColor

promotion method

2. Customize Qt Designer plug-in

The compiler uses MSVC2015 32bit

Q_INTERFACES declares the implementation interface

Q_PLUGIN_METADATA declares the metadata name

Put the dll and lib in the plug-in directory

D:\Qt\Qt5.9.1\Tools\QtCreator\bin\plugins\designer

D:\Qt\Qt5.9.1\5.9.1\msvc2015\plugins\designer

QWT is an open source project based on the LGPL copyright agreement and can generate various statistical charts.

Comparison of QT and MFC message mechanisms:

MFC's message mechanism is actually a message mapping mechanism. Programmers need to add custom messages and corresponding processing functions to the message mapping table. Asynchronous and synchronous messages are implemented through PostMessage and SendMessage.

QT's signal and slot mechanism is that signals and slot functions are dynamically linked through QObject::connect and then stored in the meta-object system. The signal is sent through emit, and the corresponding slot function is executed.

Compare

Qt's signals and slots are dynamically linked, while MFC's message mapping is static

Qt's signals support custom parameters and are type safe

In multi-threading, MFC needs to publish messages to known thread objects, while Qt does not consider the signal-slot relationship between multi-threads.

Summarize

Compared with MFC's message mechanism, Qt is more convenient to use. The biggest advantage is that Qt supports dynamic link signal slots.

4. Project related

1. Positioning problem:

I would like to ask, if there is a problem (Bug) in the software, how to quickly locate it? What are the main methods?

Answer: Print output/code debugging/logging/analysis tools/discuss with colleagues.

1) Dichotomy positioning skills

No matter how complex the code is, you can generally locate the problem using the dichotomy locating technique.

Some specific methods for dealing with bugs can be extended from the dichotomy positioning technique, such as: dichotomizing input data, dichotomizing code versions, commenting out part of the code, inserting tentative code in different locations, and dichotomizing the running environment.

2) IDE debugging

The VS debug function of the IDE is almost immediate. It can add breakpoints and single-step debugging.

Single-step debugging can make us clearer about the code logic, execution sequence, and various intermediate results.

As for bugs that are prone to errors, debugging them with an IDE is perfect.

3) Read the program again

For novice programmers, if there is a bug in the code, they can re-read the program. This method is the most effective and fastest way to debug.

4) Must kill, rewrite it

If you find that you can't find the BUG anyway, and the code is just complicated and not very long, just rewrite the code!

5) Little yellow duck debugging method

The little yellow duck debugging method is one of the methods often used by programmers to debug code.

The little yellow duck doesn't understand programming, so we can inspire him by explaining to him what each line of programming does.

Memory leaks and solutions:

What is a memory leak?

Simply put, it means that a piece of memory space is applied for and is not released after use. (1) After new and malloc apply for resources, delete and free are not used to release them; (2) When a subclass inherits a parent class, the parent class destructor is not a virtual function. (3) The Windows handle resource is not released after use.

How to detect?

First: good coding habits, use memory allocation functions, once used, remember to use the corresponding function to release it.

Second: Manage the pointers of the allocated memory in the form of a linked list. Delete them from the linked list after use. The linked list can be checked at the end of the program.

Third: Use smart pointers.

Fourth: Some common tool plug-ins, such as ccmalloc, Dmalloc, Leaky, Valgrind, etc.

Database related

what is transaction

Concurrency control

Atomicity, consistency, isolation, persistence

valueChanged(int)

QMutex mutex;

QMutexLocker locker(&mutex);

waitForReadyRead()

Commonly used design structures:

Factory Method Factory Method defines an interface for creating objects, letting subclasses decide which class to instantiate

Singleton ensures that a class has only one instance and provides a global access point to it

Prototype creates new objects by copying the prototype object.

Adapter Adapter converts the interface of a class into another desired interface, so that originally incompatible interfaces can work together.

Observer Observer defines a one-to-many dependency relationship between objects. When the state of an object changes, all objects that depend on it are notified and automatically updated.

Singleton: Lazy Man Mode and Hungry Man Mode

The trick is that once the class is loaded, the singleton is initialized to ensure that the singleton already exists when getInstance is used; thread safety.

The lazy man is lazy and only goes back to initialize the singleton when getInstance is called;

It is not thread-safe. It can only be locked when called before instantiation, but not later.

The new features of C++ mainly include syntax improvements and standard library expansion, mainly including the following 11 points:

Grammar improvements

(1) Unified initialization method, allowing constructors or other functions to use initialization lists like parameters

(2) Member variables are initialized by default

(3) Type derivation The auto keyword is used to define variables, and the compiler can automatically determine the type (prerequisite: initialize a variable when defining it)

(4) decltype finds the type of expression

(5) Smart pointer shared_ptr

(6) Null pointer nullptr (originally NULL)

nullptr represents a null pointer and is a keyword

NULL is an old version and is a macro of 0

(7) Range-based for loop

(8) Rvalue references and move semantics allow programmers to consciously reduce deep copy operations

Standard library expansion (adding some new template classes to STL, which is easier to use)

(9) Unordered container (hash table) The usage and function are exactly the same as map. The difference is that the hash table is more efficient.

(10) Regular expression A regular expression can be considered to be essentially a string that describes a specific pattern of strings.

(11) Lambda expression


Benefits of this article, receive free Qt development learning materials package and technical videos, including (Qt practical project video tutorial + code, C++ Language foundation, C++ design pattern, introduction to Qt programming, QT signal and slot mechanism, QT interface development-image drawing, QT network, QT database programming, QT project practice, QSS, OpenCV, Quick module, interview questions, etc.) ↓↓↓ ↓↓↓See below↓↓Click at the bottom of the article to receive the fee↓↓

Guess you like

Origin blog.csdn.net/hw5230/article/details/134950303