The Swede first dispatched the rebound from his saved penalty, then tapped his second into an empty net just three minutes later. Romelu Lukaku pulled one back 29 minutes in, but that was all Inter could muster.
As a result, Milan won their first derby in nine matches, since January 2016, and also ended Inter’s four-match winning streak in the fixture.
Milan now move top of the Serie A table having won all four of their matches this season, with Inter languishing in seventh, though could drop further after the weekend results.
Both teams were quick out the blocks, and it was Milan who looked the more likely before they were awarded a penalty.
Aleksandar Kolarov tackled Ibrahimovic from behind and clipped the Swede’s heels resulting in referee Maurizio Mariani pointing to the spot.
Ibrahimovic was denied by Samir Handanovic, but he put the ball in the back of the net at the second attempt.
Moments later, Ibrahimovic doubled the lead for Milan. Rafael Leao whipped a brilliant ball into the No.11 who was unmarked at the back post and he side-footed into the net.
Half an hour in Inter got themselves back into the game when Ivan Perisic made it to the goal line and his low cross was missed by Gianluigi Donnarumma before rolling into the path of Lukaku, who made no mistake from close range.
Inter continued to dominate the second half and Arturo Vidal played a brilliant ball over the defence into the path of Hakimi, but the former Real Madrid man out his diving header wide of the far post.
Made Krunic had a brilliant opportunity to kill the game off as he was put through on goal by Samu Castillejo, but he could only smash his effort well over the crossbar.
The referee then awarded a penalty after Lukaku was brought down in the box by Donnarumma, and after consultation with VAR, the decision was overturned after an offside earlier in the move.
Try as they might, Inter were unable to break a resolute Milan defence for a second time.