MFC:不结合文档和视图使用数据库类

有时,你可能不想在数据库应用程序中使用框架的文档/视图体系结构。 本主题介绍:

不需要文档的情况

一些应用程序具有独特的文档概念。 这些应用程序通常使用“打开文件”命令将存储中的所有文件或大部分文件加载到内存中。 它们使用“保存文件”或“另存为”命令将更新的文件一次性写回到存储中。 用户看到的是数据文件。

但是,某些类别的应用程序不需要文档。 数据库应用程序按照事务运行。 应用程序从数据库选择记录并将其呈现给用户,通常一次呈现一条记录。 用户看到的通常是一条当前记录,这可能是内存中唯一的一条记录。

如果应用程序不需要使用文档来存储数据,你可以省去部分或全部框架文档/视图体系结构。 省去的数量取决于你要使用的方法。 你可能会:

  • 使用最少文档作为存储与数据源的连接的位置,但无需使用常规文档功能(如序列化)。 如果你需要多个数据视图并希望同步所有视图,同时一次性更新它们等,这非常有用。

  • 使用直接在其中绘制的框架窗口,而不是使用视图。 在这种情况下,可省略文档,并将任何数据或数据连接存储在框架窗口对象中。

针对文档和视图的应用程序向导选项

MFC 应用程序向导的“选择数据库支持”中有多个选项,下表列出了这些选项。 如果使用 MFC 应用程序向导创建应用程序,所有这些选项都会生成带有文档和视图的应用程序。 某些选项提供文档和视图(可省略不需要的文档功能)。 有关详细信息,请参阅 MFC 应用程序向导的数据库支持

选项 视图 文档
派生自 CView 不提供数据库支持。 这是默认选项。

如果在 MFC 应用程序向导页上选择“文档/视图体系结构支持”,则可获得完整的文件支持,包括序列化和“文件”菜单上的“新建”、“打开”、“保存”和“另存为”命令。 请参阅不带文档的应用程序
仅头文件 派生自 CView 为应用程序提供基本级别的数据库支持。

包含 Afxdb.h。 添加链接库,但不创建任何特定于数据库的类。 稍后可以创建记录集,并使用它们检查和更新记录。
不具有文件支持的数据库视图 派生自 CRecordView 提供文档支持,但不提供序列化支持。 文档可以存储记录集并协调多个视图;不支持序列化或“新建”、“打开”、“保存”和“另存为”命令。 请参阅带有最少文档的应用程序。 如果包含数据库视图,则必须指定数据源。

包含数据库头文件、链接库、记录视图和记录集。 (仅适用于在 MFC 应用程序向导的应用程序类型页上选择了“文档/视图体系结构支持”的应用程序。
具有文件支持的数据库视图 派生自 CRecordView 提供完整的文档支持,包括序列化和文档相关“文件”菜单命令。 数据库应用程序通常基于记录运行,而不是基于文件运行,因此不需要序列化。 但是,序列化可能有特殊用途。 请参阅带有最少文档的应用程序。 如果包含数据库视图,则必须指定数据源。

包含数据库头文件、链接库、记录视图和记录集。 (仅适用于在 MFC 应用程序向导的应用程序类型页上选择了“文档/视图体系结构支持”的应用程序。

有关序列化的替代项和序列化的替代用法的讨论,请参阅序列化:序列化与数据库输入/输出

带有最少文档的应用程序

MFC 应用程序向导有两个选项,用于支持基于表单的数据访问应用程序。 每个选项都可创建一个 CRecordView 派生的视图类和一个文档。 它们的区别在于在文档中呈现的内容不同。

不具有文件支持的文档

如果不需要文档序列化,请选择应用程序向导数据库选项“不具有文件支持的数据库视图”。 此文档具有以下用途:

  • 这是用于存储 CRecordset 对象的方便位置。

    此用法与普通文档概念相似:文档存储数据(在本例中为记录集),并且视图是文档的视图。

  • 如果应用程序显示多个视图(例如多个记录视图),则文档支持协调这些视图。

    如果多个视图显示相同的数据,当任何视图更改数据时,你可以使用 CDocument::UpdateAllViews 成员函数来协调对所有视图的更新。

通常对基于表单的简单应用程序使用此选项。 应用程序向导自动为此类应用程序提供简便结构。

具有文件支持的文档

当你具有与文档相关的“文件”菜单命令和文档序列化的替代用法时,请选择应用程序向导数据库选项“具有文件支持的数据库视图”。 对于程序的数据访问部分,可以采用不具有文件支持的文档中所述的相同方式使用文档。 例如,可以使用文档的序列化功能来读取和写入序列化的用户配置文件文档,该文档可存储用户首选项或其他有用信息。 有关详细信息,请参阅序列化:序列化与数据库输入/输出

应用程序向导支持此选项,但你必须编写可对文档进行序列化的代码。 将序列化信息存储在文档数据成员中。

不带文档的应用程序

有时你可能想要编写不使用文档或视图的应用程序。 如果不使用文档,可以将数据(例如 CRecordset 对象)存储在框架窗口类或应用程序类中。 任何其他要求都取决于应用程序是否提供用户界面。

具有用户界面的数据库支持

如果你具有用户界面(例如控制台命令行接口除外),应用程序将直接绘制到框架窗口的工作区而不是视图。 此类应用程序不使用 CRecordViewCFormViewCDialog 作为主用户界面,但通常使用 CDialog 作为普通对话框。

编写不具有文档的应用程序

由于应用程序向导不支持创建不具有文档的应用程序,因此你必须编写自己的 CWinApp 派生类,并根据需要创建一个 CFrameWndCMDIFrameWnd 类。 重写 CWinApp::InitInstance 并将应用程序对象声明为:

CYourNameApp theApp;

此框架仍提供消息映射机制和许多其他功能。

独立于用户界面的数据库支持

某些应用程序不需要用户界面,或者只需要最少用户界面。 例如,假设你正在编写:

  • 中间数据访问对象,其他应用程序(客户端)调用该对象在应用程序与数据源之间进行特殊数据处理。

  • 无需用户干预即可处理数据的应用程序,例如将数据从一种数据库格式移动到另一种数据库格式的应用程序,或执行计算和批量更新的应用程序。

由于没有文档拥有 CRecordset 对象,因此你可能想要将其作为内嵌数据成员存储在 CWinApp 派生的应用程序类中。 替代方案包括:

  • 完全不保留永久 CRecordset 对象。 可以将 NULL 传递给记录集类构造函数。 在这种情况下,框架使用记录集的 GetDefaultConnect 成员函数中的信息创建临时 CDatabase 对象。 这是最有可能的替代方法。

  • 使 CRecordset 对象成为全局变量。 此变量应是指向在 CWinApp::InitInstance 重写中动态创建的记录集对象的指针。 这样就无需在初始化框架之前尝试构造对象。

  • 像在文档或视图的上下文中一样使用记录集对象。 在应用程序或框架窗口对象的成员函数中创建记录集。

另请参阅

MFC 数据库类