De façon générale, l'état interne d'un système peut être partiellement observé, par exemple via le résultat d'une série d'expérimentations, mais pas complètement. Prenons l'exemple d'un distributeur de boissons, qui accepte diverses pièces de monnaie et qui est capable de rendre la monnaie. L'ensemble des pièces et l'ensemble des boissons qu'il contient à un moment donné constituent l'état interne du distributeur. Cet état ne peut pas être complètement connu. Mais certaines expériences, c'est-à-dire certaines interactions avec le système, peuvent apporter des informations sur son état. Les seules interactions possibles sont : introduire des pièces, appuyer sur un bouton, retirer une boisson, prendre la monnaie. Un utilisateur normal ne peut pas ajouter des boissons, ni connaître le montant de la caisse, ni partir avec. C'est ce genre de modélisation que la programmation à objet facilite.
Tout programme Java est une mixture de traits applicatifs, impératifs et objets : les programmes sont organisés dans le style objet, lequel recourt à des expressions (style applicatif) et à des structures de contrôle (style impératif). L'approche orientée objet de la programmation tente de représenter un algorithme comme une communauté d'organismes vivants, chacun étant créé, disposant de ses propres ressources, d'un état interne, ayant éventuellement son propre comportement et interagissant avec les autres membres de la communauté. Ceci reste de l'ordre de la métaphore, mais conduit en pratique à incorporer les instructions dans la définition même des objets, de sorte que contrôle et données cessent d'être découplés comme c'était le cas de l'approche impérative. C++ et, plus récemment, Java et Objective Caml, sont des langages représentatifs de ce style de programmation.