The talk is quite interesting, and he does hit a few points right. However, I agree with Nexus. He is too involved with his own environment that he simply can't explain objectively what he means to.
He swallows his own words most of the time and complicates the idea he wants to pass on, but in the end, its all about shifting our code towards efficient cache use, as well as writing code that is favorable to memory access patterns on modern machines.
From what I can see, there are two main things he advocates:
1) Whenever possible, put your data in sequential chunks for faster processing, as pulling/pushing data from memory is one of the most expensive things you can do in realtime applications; Even when this implies sacrificing something else, its worth it because cache efficiency is the most powerful optimization you can do.
2) Be careful with how you access your data, to avoid for example, load-hit-store hangs; So, be careful how we read and write to our variables etc.
I just think he is too extreme about it and became a fanboy of himself, as this kind of design is not antagonistic to other design patterns or OOP.
--
In the end, if you are developing a game, you should just think what entities you have and how they relate to each other. Then apply these principles where it makes sense to.
Let me try to give a nice example. Imagine you are making a nice shmup with potentially hundreds or thousands of bullets in the screen at once; let's take the bullets as a prime example for data oriented design. They will all be moving every frame, usually very fast, so we know we will have a lot of bullets, and they all have movement in common. We know allocation is an expensive operation, especially if its happening every frame hundreds of times, so we automatically know we need a pool for optimal usage; we preallocate a ton of bullets using a std::vector<Bullet> (for example) and can almost assume we will never need another allocation for bullets.
Now, we know that every frame we can just iterate a cache efficient structure to update the bullet transforms with an efficient calculation. This is pretty much the most efficient way to go about bullet processing. But, the key here is that laying our data in such arrays of structures is NOT antagonistic to having our GameObjects and typical OOP hierarchies.
One of the most beautiful ways to go about using both approaches together (in my opinion) is to use "deferred data" in our classes. This means essentially that our classes still can access the data exactly like the old days, completely internally, but the data is not allocated there anymore, but rather in an external block of memory. Instead, a pointer or handle is used to access it every time it is needed.
Using the above example, we already solved efficient iteration and behavior updating of our bullets in a good way. Now, let's say each of our bullet-shooting GameObjects wants to render bullets in different ways, there is no need to pollute the Bullet class with all this rendering data with various types etc. We simply keep track of the handles to the right bullets in our classes, and use their data to render the bullets however we want to.
To make sure our simple integer handles stay valid, depending on the nature of our pool container etc, we can use "roster" systems, an additional array of indices that remaps our handles to the actual indices of the real pool. Since many pools like to have "alive" instances together for even quicker iteration, this means handles would break often, but not with our roster system, which would ensure valid handles. There are many ways to go about this, but I do believe this is the core of what data oriented design is. Sorry for the wall of text.