Last active
December 12, 2015 03:58
-
-
Save lawrencelomax/4711119 to your computer and use it in GitHub Desktop.
ARC Retain/Release overhead in tight loops
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
/** | |
An inline (read: no overhead) function that will perform the physics increment for a given particle | |
@return A boolean for whether the particle has expired and needs to be removed | |
*/ | |
extern inline BOOL updateParticle(BILParticleAtomConventional * atom, BILParticleModel * model, NSTimeInterval deltaTime) | |
{ | |
// Time to Live | |
atom->atom.timeToLive -= deltaTime; | |
// Return early if expired | |
if(atom->atom.timeToLive <= 0) | |
{ | |
atom->atom.timeToLive = -1; | |
return YES; | |
} | |
// Mode A: gravity, direction, tangential accel & radial accel | |
if(model.emitterMode == BILParticleModelEmitterModeGravity) | |
{ | |
__unsafe_unretained BILParticleModelGravity * gravityModel = (BILParticleModelGravity *)model; | |
// Vector from the start position of this particle | |
GLKVector2 displacementFromStart = GLKVector2Subtract(atom->atom.position, atom->atom.startPosition); | |
// Dont divide by zero | |
if(displacementFromStart.x != 0 || displacementFromStart.y != 0) | |
displacementFromStart = GLKVector2Normalize(displacementFromStart); | |
// Radial & Tangential Acceleration | |
GLKVector2 radialAcceleration = GLKVector2MultiplyScalar(displacementFromStart, atom->mode.gravity.radialAcceleration); | |
// Tangential Acceleration | |
GLKVector2 tangentialAcceleration = displacementFromStart; | |
float newY = tangentialAcceleration.x; | |
tangentialAcceleration.x = -tangentialAcceleration.y; | |
tangentialAcceleration.y = newY; | |
tangentialAcceleration = GLKVector2MultiplyScalar(tangentialAcceleration, atom->mode.gravity.tangentialAcceleration); | |
// Component of all accelerations | |
GLKVector2 accelerationVector = GLKVector2Add(gravityModel.gravity, GLKVector2Add(tangentialAcceleration, radialAcceleration)); | |
//GLKVector2 accelerationVector = model.gravity; | |
// Velocity Delta (accelleration * time) | |
GLKVector2 velocity = GLKVector2MultiplyScalar(accelerationVector, deltaTime); | |
// Velocity (velocity + deltaVelocity) | |
velocity = GLKVector2Add(atom->mode.gravity.velocity, velocity); | |
// Update Particle Velocity | |
atom->mode.gravity.velocity = velocity; | |
// Update Particle Position (position + (velocity * time)) | |
atom->atom.position = GLKVector2Add(atom->atom.position, GLKVector2MultiplyScalar(velocity, deltaTime)); | |
} | |
// Mode B: radius movement | |
else | |
{ | |
// Update the angle and radius of the particle. | |
atom->mode.radial.angle += atom->mode.radial.anglePerSecond * deltaTime; | |
atom->mode.radial.radius += atom->mode.radial.deltaRadius * deltaTime; | |
GLKVector2 position = atom->atom.startPosition; | |
position.x += (- cosf(atom->mode.radial.angle) * atom->mode.radial.radius); | |
position.y += (- sinf(atom->mode.radial.angle) * atom->mode.radial.radius); | |
atom->atom.position = position; | |
} | |
// Interpolate Color | |
atom->atom.color.r += (atom->delta.deltaColor.r * deltaTime); | |
atom->atom.color.g += (atom->delta.deltaColor.g * deltaTime); | |
atom->atom.color.b += (atom->delta.deltaColor.b * deltaTime); | |
atom->atom.color.a += (atom->delta.deltaColor.a * deltaTime); | |
// Modify the Particle size | |
atom->atom.size += (atom->delta.sizeDelta * deltaTime); | |
atom->atom.size = MAX(0, atom->atom.size); | |
// Update the Angle | |
atom->atom.rotation += (atom->delta.rotationDelta * deltaTime); | |
return NO; | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
The retain and release that ARC puts in on line 21 accounts for 90% of the cycles for this loop. Placing the __unsafe_unretained here removes ARCs influence entirely. All this is, is a cast of a parameter!
Trace Before

Trace After

CPU Usage Before

CPU Usage After
