0

私たちはポータブルコード(win + macOs)を作成しており、コードが頻繁にクラッシュするため、コードをより堅牢にする方法を検討しています...(通常はオーバーフローまたは初期化の誤り):-(

私は、Google Chromeがすべてのタブにプロセスを使用することを読んでいたので、何か問題が発生した場合、プログラムは完全にクラッシュせず、そのタブのみがクラッシュします。それはかなりいいと思うので、やってみるかもしれません!

だから私は誰かが私がより堅牢なc++コードを構築するのを助けることができるいくつかのヒント、ヘルプ、読書リスト、コメント、または何かを持っているかどうか疑問に思いました(ポータブルは常により良いです)。

同じトピックで、プロセス用のポータブルライブラリ(ブーストなど)があるかどうかも疑問に思っていましたか?

どうもありがとう。

4

12 に答える 12

5

私は多数のマルチプラットフォームC++アプリで開発しました(最大は150万行のコードで、7つのプラットフォーム(AIX、HP-UX PA-RISC、HP-UX Itanium、Solaris、Linux、Windows、OS X)で実行されます) 。実際、投稿にはまったく異なる2つの問題があります。

  1. 不安定。コードが安定していません。修理する。

    • ユニットテストを使用して、論理的な問題を見つけてから殺してください。
    • 明らかでない場合は、デバッガーを使用してクラッシュの原因を特定します。
    • Boostおよび同様のライブラリを使用します。特に、ポインタタイプは、メモリリークを回避するのに役立ちます。
  2. クロスプラットフォームコーディング。

    • 繰り返しになりますが、可能な場合はこのために設計されたライブラリを使用してください。特にGUIビットの場合。
    • もう少し作業が必要な場合でも、可能な限り標準(ANSIとgcc / MSVC、POSIXスレッドとUnix固有のスレッドモデルなど)を使用してください。プラットフォーム固有のコードを最小化することは、全体的な作業が少なくなり、学習するAPIが少なくなることを意味します。
    • 分離、分離、分離。異なるプラットフォームのインライン#ifdefはできるだけ避けてください。代わりに、プラットフォーム固有のコードを独自のヘッダー/ソース/クラスに貼り付け、ビルドシステムと#includesを使用して適切なコードを取得します。これにより、コードをクリーンで読みやすくすることができます。
    • 「long」、「int」、「short」などの代わりに、可能な限りC99整数型を使用してください。そうしないと、32ビットプラットフォームから64ビットプラットフォームに移行したときに、longが突然変化します。 4バイトから8バイトまで。そして、それがネットワーク/ディスクなどに書き込まれたことがある場合は、プラットフォーム間の非互換性に遭遇します。

個人的には、最初に(機能を追加せずに)コードを安定させてから、クロスプラットフォームの問題に対処しますが、それはあなた次第です。Visual Studioには優れたデバッガーがあることに注意してください(上記のコードベースは、その理由だけでWindowsに移植されました)。

于 2008-09-17T17:09:16.903 に答える
5

Chrome の回答は、エラーの軽減に関するものであり、コードの品質に関するものではありません。Chrome が行っていることを行うことは、敗北を認めることです。

  1. プログラマーが自分の作業をテストするだけではない、より良い QA。
  2. 単体テスト
  3. 回帰試験
  4. 他の企業が使用しているベスト プラクティスを読んでください。

率直に言うと、オーバーフローや不適切な初期化が原因でソフトウェアが頻繁にクラッシュする場合は、簡単に修正できない非常に基本的なプログラミング品質の問題があります。それはハッシュと意地悪に聞こえますが、それは私の意図ではありません. 私の言いたいことは、悪いコードの問題があなたの主な関心事でなければならないということです (私はそう確信しています)。Chrome や、プログラムの欠陥を検出するために例外処理を自由に使用するようなことは、実際の問題から注意をそらすだけです。

于 2008-09-17T16:17:49.193 に答える
1

あなたは本当に、本当にChromeがしていることをしたくありません、それはおそらくあなたが望むことに対してかなりやり過ぎであるプロセスマネージャーを必要とします。

Boostのスマートポインタ、またはC++の参照カウントまたはガベージコレクションを提供する別のツールを使用して調査する必要があります。

または、頻繁にクラッシュする場合は、C++バインディングを持つスクリプト言語でアプリケーションのパフォーマンスが重要でない部分を作成することを検討してください。

于 2008-09-17T16:10:09.697 に答える
1

スコットマイヤーズの効果的なC++より効果的なC++は非常に優れており、読むのが楽しいです。

スティーブマコネルのコードコンプリートは、ジェフアトウッドを含む多くの人のお気に入りです。

Boostライブラリはおそらく優れた選択肢です。私が働いているあるプロジェクトではそれらを使用しています。私はWIN32スレッドのみを使用しました。

于 2008-09-17T16:15:26.470 に答える
1

私はトーラックに同意します。

不適切な初期化やオーバーフローは、コードの品質が低いことを示しています。

Google がそのようにしたのは、ページで実行されたコードを制御する方法がない場合があったためです (プラグインの不具合などにより)。したがって、低品質のプラグインを使用している場合 (それは起こります)、Google のソリューションが適している可能性があります。

しかし、頻繁にクラッシュするプラグインのないプログラムは、単に書き方が悪いか、非常に複雑であるか、非常に古い (そして多くのメンテナンス時間を欠いている) だけです。開発を停止し、すべてのクラッシュを調査する必要があります。Windows では、モジュールを PDB (プログラム データベース) でコンパイルし、クラッシュするたびにデバッガーをアタッチします。

内部テストも追加する必要があります。次のパターンは避けてください。

doSomethingBad(T * t)
{
   if(t == NULL) return ;

   // do the processing.
}

エラーが存在するため、これは非常に悪い設計であり、今回は回避するだけです。しかし、このガードのない次の関数はクラッシュします。エラーに近づくには、早くクラッシュする方がよいでしょう。

代わりに、Windows で (MacOS にも同様の API が必要です)

doSomethingBad(T * t)
{
   if(t == NULL) ::DebugBreak() ; // it will call the debugger

   // do the processing.
}

(このコードを直接使用しないでください... クライアントに渡さないように定義に入れます...) 自分に合ったエラー API (例外、DebugBreak、assert など) を選択できますが、それを使用してください。コードが何かが間違っていることを認識した瞬間に停止します。

可能な限り C API を避けてください。C++ のイディオム (RAII など) とライブラリを使用します。

等..

PS: 例外を使用する場合 (これは良い選択です)、キャッチ内にそれらを隠さないでください。エラーが存在するため、問題が悪化するだけですが、プログラムは続行しようとし、後でクラッシュすることがあり、その間に触れたものはすべて破損します。

于 2008-09-17T16:54:33.227 に答える
1

ターゲット プロジェクトが何であるかについては触れていません。タブごとにプロセスを持つことは、必ずしもより「堅牢な」コードを意味するわけではありません。移植性に関係なく、テスト付きの堅実なコードを書くことを目指すべきです - 良い C++ コードを書くことについて読んでください :)

移植性セクションに関しては、初日から両方のプラットフォームでテストしていることを確認し、プラットフォーム固有の問題が解決されるまで新しいコードが書かれていないことを確認してください。

于 2008-09-17T16:09:47.013 に答える
0

プログラムに例外処理を追加して、これらの種類の障害をキャッチし、無視することができます(詳細はプラットフォーム固有ですが)...しかし、それは非常に両刃の剣です。代わりに、プログラムで例外をキャッチし、分析用のダンプファイルを作成することを検討してください。

プログラムが予期しない動作をした場合、内部状態について何を知っていますか?クラッシュしたルーチン/スレッドがいくつかの重要なデータ構造を破壊したのではないでしょうか?たぶん、エラーを見つけて続行しようとすると、ユーザーは作業中のものをすべて保存し、破損をディスクにコミットしますか?

于 2008-09-17T16:12:38.317 に答える
0

終了する唯一の方法はプログラムがクラッシュすることであり、いつでもクラッシュする可能性があるという考えで構築してください。そのように構築すると、クラッシュによってデータが失われることはありません。1、2年前にそれについての記事を読みました。悲しいことに、私はそれへのリンクを持っていません。

それをある種のクラッシュダンプと組み合わせて、問題を修正できるようにメールで送信してもらいます。

于 2008-09-17T16:34:52.507 に答える
0

15年以上のWindows開発の後、私は最近、最初のクロスプラットフォームC ++アプリ(Windows / Linux)を作成しました。方法は次のとおりです。

  • STL
  • ブースト。特に、ファイルシステムとスレッドライブラリ。
  • ブラウザベースのUI。アプリはHTTPを実行し、UIはXHTML / CSS / JavaScript(Ajaxスタイル)で構成されます。これらのリソースはサーバーコードに埋め込まれ、必要に応じてブラウザに提供されます。
  • 大量の単体テスト。完全にTDDではありませんが、近いです。これは実際に私が開発する方法を変えました。

LinuxビルドにNetBeansC++を使用し、すぐに完全なLinuxポートを使用しました。

于 2008-09-17T18:29:32.000 に答える
0

Linux バージョンをコンパイルしてValgrindで実行することをお勧めします。

Valgrind は、メモリ リーク、初期化されていないメモリ読み取り、およびその他の多くのコードの問題を追跡します。強くお勧めします。

于 2008-09-17T16:42:41.430 に答える
0

より安定したコードを書くことに加えて、あなたの質問に答える 1 つのアイデアがあります。

プロセスまたはスレッドを使用しているかどうか。小規模/単純なウォッチドッグ プログラムを作成できます。次に、他のプログラムがそのウォッチドッグに登録します。いずれかのプロセスまたはスレッドが停止した場合、ウォッチドッグによって再開できます。もちろん、同じバグのあるスレッドを再起動し続けないように、何らかのテストを行いたいと思うでしょう。つまり、5 回再起動し、5 回目以降はプログラム全体をシャットダウンし、ファイル / syslog に記録します。

于 2008-09-17T16:21:29.170 に答える
0

デバッグ シンボルを使用してアプリをビルドし、例外ハンドラーを追加するか、クラッシュ ダンプを生成するようにワトソン博士を構成します (drwtsn32.exe /i を実行して、デバッガーとしてインストールします。構成ダイアログをポップする /i は使用しません)。アプリがクラッシュした場合、windbg またはビジュアル スタジオでコールスタックと変数を確認することで、どこで問題が発生したかを調べることができます。

詳細については、シンボル サーバーの google を参照してください。

明らかに、例外処理を使用してより堅牢にし、スマート ポインターを使用できますが、バグを修正するのが最善です。

于 2008-09-17T16:24:06.560 に答える