複雑なプログラムには、何らかの種類の間接指定が必要です(再帰的または可変サイズのデータ構造など)。ただし、ポインターを使用してこの間接化を実装する必要はありません。
高レベルのプログラミング言語の大部分(アセンブリではない)はかなりメモリセーフであり、無制限のポインタアクセスを許可しません。Cファミリーはここでは奇妙なものです。
CはBから進化しました。Bは生のアセンブリを非常に薄く抽象化したものです。Bには、単語という単一のタイプがありました。この単語は、整数またはポインタとして使用できます。メモリ全体が単一の連続した配列と見なされる場合、これら2つは同等です。Cはこのかなり柔軟なアプローチを維持し、本質的に安全でないポインター演算を引き続きサポートしました。Cの型システム全体は、後付けになっています。メモリアクセスに対するこの柔軟性により、Cはその主な目的であるUnixオペレーティングシステムのプロトタイピングに非常に適しています。もちろん、UnixとCは非常に人気があることが判明したため、Cはメモリへのこの低レベルのアプローチが実際に必要でないアプリケーションでも使用されます。
C以前のプログラミング言語(Fortran、Pascal、Cobol、LispなどのAlgol方言など)を見ると、それらのいくつかはCのようなポインターをサポートしています。特に、1965年にAlgol Wに対してヌルポインターの概念が考案されました。しかし、これらの言語はいずれもCに似た効率的な低抽象化システム言語にはなりませんでした。業界レベルの言語よりも多くの研究プロジェクトであり、Cobolはビジネスアプリケーションに焦点を当てていました。
ガベージコレクションは、50年代後半、つまりC(70年代前半)のかなり前から存在していました。GCが正しく機能するには、メモリの安全性が必要です。Cの前後の言語はGCを通常の機能として使用していました。もちろん、それは言語をはるかに複雑にし、場合によっては遅くします。これは、メインフレームの時代に特に顕著でした。GC言語は、研究指向(Lisp、Simula、MLなど)であるか、強力なワークステーション(Smalltalkなど)を必要とする傾向がありました。
一般に、より小さく、より強力なコンピューターコンピューティングとGC言語がより一般的になりました。非リアルタイムアプリケーション(およびその場合もある)では、GCが推奨されるアプローチになりました。しかし、GCアルゴリズムも熱心な研究の対象となっています。代替として、特に過去30年間で、GCを使用しないより優れたメモリの安全性もさらに開発されました。注目すべき革新は、RAIIとC ++のスマートポインターおよびRustのライフタイムシステム/借用チェッカーです。
Javaはメモリセーフなプログラミング言語であるために革新されませんでした。基本的に、GCed、メモリセーフなSmalltalk言語のセマンティクスを取り、C ++の構文と静的型付けと組み合わせました。その後、より優れたシンプルなC / C ++として販売されました。しかし、表面的にはC ++の子孫にすぎません。Javaのポインターの欠如は、C ++データモデルを拒否することよりも、Smalltalkオブジェクトモデルに負うところが大きいです。
したがって、Java、Ruby、C#などの「現代の」言語は、Cのような生のポインターの問題を克服するものとして解釈されるべきではありません。またはLisp。