'windows.h',其他平台呢?

'windows.h', what about other platforms?

我在 windows 上使用 visual studio,我有一个名为 windows.h 的头文件,这当然让我可以访问 win32 API.

但是当我尝试使用其他平台时 API 例如 linux API。我没有找到任何具有该名称的头文件,这意味着我不能使用除 windows、

之外的任何其他 OS API

现在的问题是:例如,如果我不想制作跨平台程序怎么办?当我没有适当的访问它的 API 时,我尝试了一段时间的研究,但无法得到任何问题的答案,这让我现在很困扰,所以要更多具体这些是我的问题:

1- 为什么我只能使用所有其他操作系统中的 windows API? 是不是因为我在 windows 上编码,所以如果我在“其他地方”编码,它会有所不同吗? 还是与编译器本身有关?

2- 如果我想使用另一个 API 我必须使用外部库怎么办?如果是这样的话,C++ 跨平台中的标准库是怎样的,我的意思是如果它是跨平台的,那么应该存在库提供的其他平台特定的头文件吧?

  1. 关于 windows.h 库的 Wikipedia 说:

windows.h is a Windows-specific header file for the C and C++ programming languages which contains declarations for all of the functions in the Windows API, all the common macros used by Windows programmers, and all the data types used by the various functions and subsystems.


  1. Linux 没有像 Windows 那样为 window 管理 提供默认的 API 所以如果你正在编程一个图形应用程序,那么您还需要选择一个 windowing 库。

第一部分的答案是肯定的。您只能使用 Windows API,因为您正在 Windows 上编程。但是,您可以在 Windows 上 运行 Linux。一个名为 Windows Subsystem for Linux 的 Microsoft 产品允许您这样做。但即使您这样做,您也不会找到名为 linux.h 的 header,它比这更复杂。还有一个产品(我相信叫做 WINE)可以让你在 Linux 上使用 Windows API,尽管我认为它有一些问题。

标准库接口是跨平台的,但实现肯定不是。它通过抽象掉 OS 特定功能来实现这一点。如果您查看库在不同平台上的实现方式,您肯定会发现很多差异。

but when I try to use other platforms API like the linux API for example. I don't find any header file with that name

系统API没有header调用<linux>。 POSIX 操作系统规范(Linux 符合)列出了几个 header,其中包含您可以从该系统的 windows.h 中找到的功能。 POSIX 规范与 C 标准库重叠,C 标准库实现也提供了 POSIX 特定的 header。有关 header 的完整列表,请参阅 Linux 手册或 POSIX 规范。

what if I want to use another [system] API

您至少需要 API 的 header 个文件才能编译调用它们的程序。此外,您需要图书馆档案才能 link 您的程序。而且您需要告诉编译器您的目标系统。默认情况下,所有编译器都假定您的目标系统是 运行 编译器。您需要查阅编译器的文档,了解是否可以进行交叉编译以及如何进行。

或者更简单的方法:在提供 API 的系统上编译。 header 可能需要单独安装。

... how is the Standard Library in c++ cross platform

每个系统都有自己的标准库。一些标准库的实现是跨平台的,但不是全部。例如,libstdc++——它是 GNU 项目一部分的标准库,也是 Linux 中的默认标准库——可在包括 Windows 在内的许多平台上使用。相比之下,Msvc 标准库仅在 Windows.

上可用

I'm using visual studio on windows and I have this header file called windows.h which of course gives me access to the win32 API.

严格来说 windows.h 有点像 meta-header。 windows.h 中定义了一些重要的宏、标记和​​符号,但它也引入了 很多 的其他 header。如果您查看每个 Win32 API 函数的参考手册,它会告诉您该函数是在哪个 header 中声明的。让我们看一下 CreateFileA 例如:在您会在参考手册的底部找到:

Requirements


Minimum supported client Windows XP [desktop apps only]


Minimum supported server Windows Server 2003 [desktop apps onliy]


Target Platform Windows


Header fileapi.h (include Windows.h)


Library Kernel32.lib


DLL Kernel32.dll

所以这告诉我们,CreateFileA 实际上是在 fileapi.h 中声明的,并且是从 kernel32.dll 系统库中导出的。

but when I try to use other platforms API like the linux API for example.

也就是因为没有linux.hAPIheader(如果搜索Linux开发系统名为 linux.h 的文件你会发现很多,但这些文件不用于系统级别 API)。

原因是 Linux 没有自己专有的 API,而是遵循 POSIX industry standard for operating system APIs, and the Single Unix Specification maintained by the Open Group.

当然有 Linux 特定的 APIs,但您可以安全地忽略它们以进行“常规”应用程序开发;如果您正在做低级别的事情,例如编写 C 运行时库或自定义内存分配器,则需要这些。

作为开发人员,您最感兴趣的是第 2 部分(调用操作系统内核 = 系统调用)和第 3 部分(库函数)中的联机帮助页。 https://linux.die.net/man/

等同于 CreateFileA 的 POSIX 将是 open,您可以在第 2 节中找到它:https://linux.die.net/man/2/open(或 creat 系统调用,由于遗留原因而存在,但没有人使用它(或应该使用它))。

如果您查看打开的联机帮助页,它会告诉您

open(2) - Linux man page


Name

open, creat - open and possibly create a file or device

Synopsis

#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
int open(const char *pathname, int flags);
int open(const char *pathname, int flags, mode_t mode);
int creat(const char *pathname, mode_t mode);

这告诉您,为了使用 open,您需要包含 sys/types.hsys/stat.hfcntl.h。与 Windows 不同,没有包罗万象的 header 可以囊括一切。这样做的原因是,出于向后和交叉兼容性的原因 可以通过在包含 header[= 之前​​将某些宏设置为特定值来配置 header 公开的内容83=]。这些在 feature_test_macros(7) 中进行了解释,对于应用它们的函数,也在相应的手册页中提到。

I don't find any header file with that name, which mean that I can't use any other OS API than windows,

你找不到,并不代表它不存在。

now the problem here is: what if I wan't to make a cross platform program for example?

然后将所有特定于平台的内容写入一个单独的 .c 文件,该文件封装了 OS 内容。

when I don't have the appropriate access to its API

嗯,你知道。

1- why I can only use the windows API out of all the other operating systems?

因为你做不到。 Windows.h 仅在 Windows 系统上可用。

2- what if I want to use another API do I have to use an external library?

那你就用吧

请记住,在 Linux 中,图形环境不是主操作系统的一部分。它实际上是一个在系统启动时自动启动的常规程序。因此,您不会在上述联机帮助页中找到相关文档。

Linux 的默认图形环境是 Xorg(X11 显示系统的开放实现)。还有 Wayland,但经过 10 多年的开发,它的支持仍然很差,还有很多不足之处。

如果你想在与 Win32 相同的水平上对 X11 进行编程,你将不得不处理 Xlib or Xcb. However direct X11 programming is quite tedious. You probably want to use some nice application framework like Qt 或 GTK。 Qt 本身是一个跨平台框架,所以如果您限制自己只使用 Qt 功能,您的程序将完全跨平台,无需额外的努力。如果要在 GPU 上做 3D 图形,请使用跨平台 APIs OpenGL 或 Vulkan。