Here's my guess at why Matlab behaves like that:
I think that assigning to [] can be considered a special operator, i.e. a(1,:) = [] will essentially delete the first row of a. So even though size(a(1,:)) differs from size([]), I reckon the Matlab interpreter knows that this special case is not an assignment.
However a(1,:) = b when b=[] will give you a subscript dimension mismatch. I think this is correct behaviour because in this case you are assigning, and you're trying to assign a 0-by-0 to a 1-by-3 which is a dimension mismatch. The same goes for a([],:) = b, you're trying to fit a 0-by-0 into a 0-by-3 space which is again a mismatch.
So in conclusion, the second case is an assignment operator and so the error makes sense. The first case is a special delete operator and hence no error.
I have no references for any of this (this is all I could find in the docs but it doesn't really cover everything)
However I don't think this explains all the behaviour, some examples brought up from the comments:
Assume:
a = magic(3);
a2 = magic(4);
b = [];
a([],:) + a2([],:) gives a dimension mismatch error as expected.
a([],:) = a2([],:) does not throw an error... which to me is not expected
a([],:) = b(:) also does NOT throw an error... which is again quite strange, unless we can assume that the (:) operation returns a comma separated list like the {:} does (although I know that is not the case)???
These cases seem inconsistent to me.
We can expand on case 2:
a([],:) = zeros(0,0)
a([],:) = zeros(0,2)
a([],:) = zeros(0,3)
a([],:) = zeros(0,4)
only he first case throws an error and the other 3 are accepted by Matlab. Looks like this answer is just creating further questions :/