The faster you unlearn OOP, the better for you and your software
> The vast majority of essential code is not operating on just one object – it is actually implementing cross-cutting concerns. Example: when class Player hits() a class Monster, where exactly do we modify data? Monster's hp has to decrease by Player's attackPower, Player's xps increase by Monster's level if Monster got killed. Does it happen in Player.hits(Monster m) or Monster.isHitBy(Player p). What if there's a class Weapon involved? Do we pass it as an argument to isHitBy or does Player has a currentWeapon() getter?Not saying this is the right way to do things but, if you're  actually going to go 100% OO on something:Player.hits(Monster) returns HitHit takes a Player and a Monster in constructor, and has with(Weapon)You end up with:Player.hits(Monster).with(Weapon)Then Hit reaches into said objects and deals with changing the HP, and XP. You then have encapsulated the details in the actual Hit itself, which seems correct.It does read kind of nicely IMO...