(C ++のような言語の)プログラムをクロスプラットフォームにするのは何ですか?


8

私はJavaでのかなり基本的なプログラミング経験があり、C ++とPythonを試しました。Javaでは理にかなっていますが、C ++で記述した基本的なプログラムはWindowsとOS Xで問題なく動作しました。ソースファイルを他のコンピューターに送信し、コンパイルして実行することができました。プログラムはかなり基本的なもので、主に私がC ++を学ぶためにやってきた基本的なオブジェクト指向のものだけです。

もちろん、どのマシンでもC ++プログラムをコンパイルして問題なく実行することはできません。それはどの時点で起こりますか?プラットフォームはどのレベルの複雑さで問題になり始め、プログラムはどこでも実行されませんか?プラットフォーム固有のライブラリを使用するときですか?クロスプラットフォームライブラリを使用するだけで、プログラムをC ++でクロスプラットフォームにできますか?

私は自分でこれを理解しようとしましたが、見つけたものはすべて頭を悩ませるか、単に質問に答えないかのどちらかです。多くの場合、エミュレーターや、クロスプラットフォームの言語を尋ねる人々がいます。


2
プラットフォーム固有のライブラリ、非標準のコンパイラー拡張、ビットが実際にメモリ内に配置される方法への依存、およびその他の未定義/未指定の動作が、コードがプラットフォーム固有になる典型的な理由です。これらすべてを回避する場合、はいC ++はデフォルトでかなり移植可能です。
Ixrec

「クロスプラットフォームライブラリを使用するだけで、プログラムをC ++でクロスプラットフォームにできますか?」これはほとんど本当です。また、コンパイルされたマシンコードはアーキテクチャーに固有であるため、プラットフォームごとにコンパイル(バイナリーを作成)する必要もあります。
rwong

1
QtまたはPOCOフレームワークを使用できます。
Basile Starynkevitch、

回答:


6

クロスプラットフォームとモノプラットフォームの間の砂には非常に明確な線があります。

プログラムは、その上に構築された標準ライブラリによって公開されているAPIのみを使用しますか?

標準的な実装を対象とする場合、その標準を実装するプラットフォームは、理論的には、プログラムを正しくコンパイルして実行する必要があります。例外はたくさんありますが、一般的に巧妙なトリックを回避すれば、それらの例外の多くを回避できるはずです。

この問題が特にC ++で発生する理由は、C ++標準ライブラリに、重要なプログラムに役立つ多くのモジュールが含まれていなかったことが最も長いことです。並行性とGUIは2つの大きなものです。これは、C ++標準ライブラリのみを使用して構築されたプログラムが、現代のソフトウェアに期待する機能の多くを備えていないことを意味しました。

標準ライブラリでサポートされていないものを実行するクロスプラットフォームソフトウェアをどのように作成すればよいですか?

「クロスプラットフォームライブラリ」について言及しますが、実際には通常、その範囲に基づいて「フレームワーク」または「ツールキット」と呼ばれます。クロスプラットフォームのソフトウェアをC ++で作成する方法は、標準ライブラリだけでなく、ターゲットプラットフォーム上に構築するフレームワークをターゲットにすることです。

基本的に、プラットフォーム固有のビットを別のライブラリに外部化することになります。たとえば、wxWidgetsは一般的なフレームワークです。そのクラスを使用して、GUIおよび関連機能(ファイルを選択するための標準ダイアログなど)を構築できます。内部では、条件付きコンパイルを使用して、各プラットフォームのネイティブGUIを使用してGUIを実装します。しかし、ライブラリのユーザーとして、それはあなたにとって重要ではありません。


歴史的注記:2015年のここC ++コンパイラーとライブラリーは、ほとんどの場合、本当に優れています。数年前に戻りますが、それは真実ではありません。C ++は、その発足から何年も経過した1998年まで公式の標準を持っていませんでした。ベンダーがコンパイラとライブラリを更新して標準を正しく実装するのに長い時間がかかりました。ベンダー固有の拡張機能はたくさんあります(実際にはまだ存在しています)。一部のコンパイラには、非標準のヘッダーと機能がありました。コードの移植性は事実上存在しませんでした。移植性の面でのC ++の評判は依然として損なわれています。


5

プラットフォームはどのレベルの複雑さで問題になり始め、プログラムはどこでも実行されませんか?

基本的に重要なものは何でも。あなたは非自明なプログラムを記述する場合、あなたはします誤って、コンパイラ固有の方法に依存してしまうことも受注のオーバーロード、ルックス名、およびその他の複雑なものまで。さらに、標準は実際にはいくつかのコンテナを除いて何も提供しないため、実質的にすべての重要なプログラムは非標準のプラットフォーム固有の動作に依存しています。

ただし、重要なプログラムは、別のプラットフォームへの移植がいかに簡単であるかによって大きく異なります。うまくプログラムしてルールに固執していれば、かなり簡単に移植できます。また、それらをライブラリに抽象化できればボーナスもあります(Boost.Filesystemなどのライブラリがすでに提供されている場合があります)。

プログラムがプラットフォーム間で移植するのが非常に困難になるのは、本質的にプラットフォーム固有のタスクを実行する場合のみです。たとえば、特定の原子性/一貫性の保証を備えたディスクへのデータの書き込み、または、独り言を言って愚かなことをしていた場合intとポインタの間のキャストのように、最初にすべきことは決してありません。


2
確かにこれはケースを過大評価しますか?より難解なC ++コードが古いまたは低品質のコンパイラのさまざまなコンパイラバグに遭遇する可能性があることは知っていますが、合理的に標準に準拠したコンパイラは、オーバーロードや名前の検索などを同様に処理する必要があります。標準ライブラリは、I / Oと(C ++ 11以降)スレッド化を提供し、ファイルシステムのサポートは標準化されています。
Josh Kelley、

@JoshKelley:ほとんどのプログラムが必要とするものと比較して、基本的には何もありません。また、MSVCのような一部の非常に一般的なコンパイラは、オーバーロード、SFINAE、および名前のルックアップを異なる方法で実装し、さまざまな観察可能な結果を​​もたらします。
DeadMG

1

非常に簡単に言えば、プログラムをクロスプラットフォームにするのは、ある環境からソースを取得して別の環境でコンパイルし、完成した製品を期待どおりに機能させる能力です。

簡単に言えば、プログラムが利用可能であると期待しているものとターゲット環境が提供しているものとの間に完全なオーバーラップがあります。環境固有のライブラリや動作が定義されていない言語機能を使用するなど、オーバーラップが100%未満になるような操作を行うと、オーバーラップしない機能を提供できる環境にプログラムが関連付けられます。

( "プラットフォーム"は少しぎこちない言葉です。プラットフォームとしてのWindowsとUnix、またはLinux、OS X、BSDとSolarisはすべてUnixであるにもかかわらず、人々はそれらについて話すことができます。上記のいずれかを異なる環境で実行してくださいハードウェアアーキテクチャや物事はさらに曖昧になります。

幸い、この問題を緩和するための基準があります。

言語。 あなたはC ++を作成しています。これは1998年にISOによって最初に標準化されました。その標準に準拠して作成したプログラムは、コンパイルして、準拠するコンパイラとランタイムを備えた任意のプラットフォームで期待される結果で実行できます。標準から逸脱しない限り、プログラムのサイズや洗練度に制限はありません。おそらく標準に適合するプログラムが特定のプラットフォームで期待どおりに実行されない場合、そのプラットフォームでの言語の実装が疑わしくなります。多くの言語には、適合性の検証に使用できる慎重に設計されたテストスイートがあります。

Javaは、言語を標準化するだけでなく、オブジェクトコードも標準化するため、特別な言及を得ています。これにより、プログラムを再コンパイルせずにどこでも実行できるようになります。これは、オブジェクトポイントを実行できるプラットフォームカスタマイズされた仮想マシン(またはハードウェア)に追加のレイヤーを押し込んで、適合点を押し下げることによって実現されます。

API。 プログラムに特定のことをさせるために行う呼び出しも、標準化することができます。言語と同様に、これらのAPIとそれらを実装するライブラリは、呼び出し元が特定のプラットフォームに適した基本的な実装を使用して期待どおりに動作するように設定できます。そのようなAPIの1つがIEEEのPOSIX標準で、これは1980年代にUnixで起こっていた断片化を阻止する方法として生まれました。(私はその頃でした。その側面は面白くありませんでした。)標準の呼び出しと動作を定義することで、システムベンダーは、OSへの移行が、過去。POSIXは広く採用され、ほぼ30年経った今でも広く使用されています。

私は、複数のプラットフォームで実行する必要があることを知っていたので、標準に厳密に準拠した多数のプロジェクトを実行しました。私がトラブルに遭遇したのは、コードを実行する予定のすべての場所で機能するコードであり、実行しなかったいくつかの場所でうれしい驚きを与えました。


0

基本的に、プログラムの外で何かに「触れる」とき。1つの特定のケース(私はあえて唯一のケースとは言いません)は、オペレーティングシステムに関連するライブラリを使用する場合です。プロセス間で共有メモリを使用することや、コンソールに凝ったものを印刷することなど。最初のケースでは、オペレーティングシステムによって処理されているメモリにアクセスします。2番目のケースでは、画面もオペレーティングシステムによって制御されます。

GUIの実行はOSに依存しますが、クロスプラットフォームにするために作成されたGUIライブラリがあるため、そのことを心配する必要はありません。少なくとも理論的には。

クロスプラットフォームになるために重要なものを作るのは難しいです。良い点は、適切なライブラリを使用して適切なテストを行うことで、少なくともコードが大きくなりすぎない限り、ソフトウェアを移植可能にすることはそれほど難しくないということです。大きさが大きすぎるかどうかは、チームのサイズ、プログラミングの専門知識などに依存します。

弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.