Exemplo n.º 1
0
Vec2<float> abs(const Vec2<float> &v) {
	Vec2<float> rv;
	rv.x = abs_float(v.x);
	rv.y = abs_float(v.y);

	return rv;
}
Exemplo n.º 2
0
Vec4<float> abs(const Vec4<float> &v) {
	Vec4<float> rv;
	rv.x = abs_float(v.x);
	rv.y = abs_float(v.y);
	rv.z = abs_float(v.z);
	rv.w = abs_float(v.w);

	return rv;
}
Exemplo n.º 3
0
VecN<float, N> abs(const VecN<float, N> &v) {
	VecN<float, N> rv;
	for(unsigned int i=0; i < N; i++) {
		rv.v[i] = abs_float(v.v[i]);
	}
	return rv;
}
Exemplo n.º 4
0
float abs(const float v) {
	return abs_float(v);
}
Exemplo n.º 5
0
//average SGD implemented by Julius 2014.08.27
void LLC_SGD(double *w, double *x, double *centers, int *knn_idx, int knn, int d) {
    int i, j, iter=0, iter0=-1;
    float GAMMA = 2, adaGAMMA=GAMMA;
    memset(w, 0.01, knn*sizeof(double));
    
    //minimizing 0.5*||x - w*centers||2,2 + 0.5*lambda*||w||2,2
    srand(time(NULL));
    float past_grad[64] = {0};

    //w[0] = w[1] = 0.25;
    
    init_w(w, knn);
    eval_obj_iter = 0;
    while(iter < knn*30) {
        for(i=0; i<BATCH_SIZE; i++)
            batch_idx[i] = rand()%d;    //[0, 127]
        
        adaGAMMA = GAMMA*pow(1+GAMMA*BETA_SGD*(iter0+1), -0.75);
        //adaGAMMA = GAMMA;
        if(iter > knn*8)
            iter0++;
        //if(iter0 == 0)
        //    printf("============Start averaging!!============\n");
        
        //printf("adaGAMMA[%d]: %f\n", iter, adaGAMMA);
        
        float wcenters[BATCH_SIZE]={0}, sub_grad=0;
        
        //mini-batch SGD, if BATCH_SIZE = 1, then it is shrunk to SGD
        
        if(BATCH_SIZE > 1) {    //mini-batch SGD
            for(j=0; j<BATCH_SIZE; j++) {
                int idx = batch_idx[j];
                for(i=0; i<knn; i++)
                    wcenters[j] += w[i]*centers[knn_idx[i]*d+idx];
                wcenters[j] = x[idx] - wcenters[j];
            }
            
            for(i=0; i<knn; i++) {
                sub_grad=0;
                for(j=0; j<BATCH_SIZE; j++) {
                    int idx = batch_idx[j];
                    sub_grad += wcenters[j]*centers[knn_idx[i]*d+idx];
                }
                
                sub_grad /= BATCH_SIZE; //average over mini-batch gradients
                
                sub_grad += BETA_SGD*w[i];
                sub_grad *= adaGAMMA;
                
                if(abs_float(sub_grad) < 5e-4)  //neglect too small update
                    continue;
                
                w[i] += (sub_grad);
                
                w[i] = (w[i] > 1) ? 1: w[i];
                w[i] = (w[i] < -1) ? -1: w[i];
            }
        }
        else {  //SGD
            int idx = batch_idx[0];
            for(i=0; i<knn; i++)
                wcenters[0] += w[i]*centers[knn_idx[i]*d+idx];
            for(i=0; i<knn; i++) {
                sub_grad = (x[idx] - wcenters[0])*centers[knn_idx[i]*d+idx];    //calculate sub_grad[0~127]
                sub_grad += BETA_SGD*w[i];
                sub_grad *= adaGAMMA;
                
                if(abs_float(sub_grad) < 5e-4)  //neglect too small update
                    continue;
                
                double lower_bound, upper_bound;
                double tentaive_w = w[i] + sub_grad;
                if(w[i] > 0) {
                    lower_bound = 0;  //avg_w - 2*avg < x < avg_w + 2*avg
                    upper_bound = 2*w[i];
                }
                else {
                    lower_bound = 2*w[i];
                    upper_bound = 0;
                }
                
                w[i] += (sub_grad);
                
                w[i] = (tentaive_w > upper_bound) ? upper_bound: tentaive_w;
                w[i] = (tentaive_w < lower_bound) ? lower_bound: tentaive_w;
                
                w[i] = (w[i] > 1) ? 1: w[i];
                w[i] = (w[i] < -1) ? -1: w[i];
            }
        }
        
        if(iter0 == 0) {
            for(i=0; i<knn; i++)
                avg_w[i] = w[i];
        }
        if(iter0 >= 0) {
            for(i=0; i<knn; i++) {
                double past_w = avg_w[i];
                avg_w[i] = w[i] + (double)iter0/(iter0+1)*(avg_w[i]-w[i]);
                past_grad[i] = avg_w[i] - past_w;
                
                double tentaive_w = avg_w[i] + 2*past_grad[i];  //momentum is used
                
                double lower_bound, upper_bound;
                if(avg_w[i] > 0) {
                    lower_bound = -2*avg_w[i];  //avg_w - 3*avg < x < avg_w + 3*avg
                    upper_bound = 4*avg_w[i];
                }
                else {
                    lower_bound = 4*avg_w[i];
                    upper_bound = -2*avg_w[i];
                }
                avg_w[i] = (tentaive_w > upper_bound) ? upper_bound: tentaive_w;
                avg_w[i] = (tentaive_w < lower_bound) ? lower_bound: tentaive_w;
                
                avg_w[i] = (avg_w[i] > 1) ? 1: avg_w[i];
                avg_w[i] = (avg_w[i] < -1) ? -1: avg_w[i];
                
                //printf("[%d](w, grad) = (%f, %f)\n", i, avg_w[i], past_grad[i]);
            }
#ifdef SGD_DEBUGGING
            eval_obj(avg_w, x, centers, knn_idx, knn, d);
#endif
        }
        //norm_w(w, d);
        else {
#ifdef SGD_DEBUGGING
            eval_obj(w, x, centers, knn_idx, knn, d);
#endif
        }
        
        iter++;
    }
    double sum=0;
    for(i=0; i<knn; i++)
        sum += avg_w[i];
    
    for(i=0; i<knn; i++) {
        avg_w[i] /= sum;
        if(abs_double(avg_w[i]) < TOLERANCE)    //cut-off small values
            avg_w[i] = 0;
    }
    
#ifdef SGD_DEBUGGING
    printf("LLC_SGD w: (");
    for(i=0; i<knn; i++)
        printf("%f ", avg_w[i]);
    printf(")\n");
#endif
}
Exemplo n.º 6
0
Arquivo: gx.c Projeto: LWSS/gx
static void tick_physics(struct GameState *game_state, float dt)
{
    // Projectile kinematics.
    for (uint32 i = 0; i < game_state->projectile_count; ++i)
    {
        struct Projectile *projectile = &game_state->projectiles[i];

        // r = r0 + (v*t) + (a*t^2)/2
        projectile->position = vec2_add(projectile->position, vec2_mul(projectile->velocity, dt));
    }

    // Ship kinematics.
    for (uint32 i = 0; i < game_state->ship_count; ++i)
    {
        struct Ship *ship = &game_state->ships[i];

        vec2 move_acceleration = vec2_zero();

        // v = v0 + (a*t)
        ship->move_velocity = vec2_add(ship->move_velocity, vec2_mul(move_acceleration, dt));

        // r = r0 + (v*t) + (a*t^2)/2
        ship->position = vec2_add(vec2_add(ship->position, vec2_mul(ship->move_velocity, dt)), vec2_div(vec2_mul(move_acceleration, dt * dt), 2.0f));
    }

    //
    // TODO: spatial hashing
    //

    // Projectile collision.
    for (uint32 i = 0; i < game_state->projectile_count; ++i)
    {
        struct Projectile *projectile = &game_state->projectiles[i];
        struct AABB projectile_aabb = aabb_from_transform(projectile->position, projectile->size);

        // Projectile-building collision.
        for (uint32 j = 0; j < game_state->building_count; ++j)
        {
            struct Building *building = &game_state->buildings[j];
            struct AABB building_aabb = aabb_from_transform(building->position, building->size);

            if (aabb_aabb_intersection(projectile_aabb, building_aabb))
            {
                // TODO: damage building if not friendly
                destroy_projectile(game_state, projectile);
                break;
            }
        }

        // NOTE: owner may be dead and destroyed at this point, so checking for NULL might be required.
        struct Ship *owner = get_ship_by_id(game_state, projectile->owner);

        // Projectile-ship collision.
        for (uint32 j = 0; j < game_state->ship_count; ++j)
        {
            struct Ship *ship = &game_state->ships[j];
            if (ship->id == projectile->owner)
                continue;

#if 0
            // Allow projectiles to pass through teammates.
            if (ship->team == projectile->team)
                continue;
#endif

            struct AABB ship_aabb = aabb_from_transform(ship->position, ship->size);

            if (aabb_aabb_intersection(projectile_aabb, ship_aabb))
            {
                // Disable friendly fire.
                if (ship->team != projectile->team)
                    damage_ship(game_state, ship, projectile->damage);

                destroy_projectile(game_state, projectile);
                break;
            }
        }
    }

    // TODO: optimize
    // Ship collision.
    if (game_state->ship_count >= 2)
    {
        for (uint32 i = 0; i < game_state->ship_count - 1; ++i)
        {
            struct Ship *a = &game_state->ships[i];
            struct AABB a_aabb = aabb_from_transform(a->position, a->size);
            vec2 a_center = vec2_div(vec2_add(a_aabb.min, a_aabb.max), 2.0f);
            vec2 a_half_extents = vec2_div(vec2_sub(a_aabb.max, a_aabb.min), 2.0f);

            // Ship-building collision.
            for (uint32 j = 0; j < game_state->building_count; ++j)
            {
                struct Building *building = &game_state->buildings[j];
                struct AABB b_aabb = aabb_from_transform(building->position, building->size);

                if (aabb_aabb_intersection(a_aabb, b_aabb))
                {
                    vec2 b_center = vec2_div(vec2_add(b_aabb.min, b_aabb.max), 2.0f);
                    vec2 b_half_extents = vec2_div(vec2_sub(b_aabb.max, b_aabb.min), 2.0f);

                    vec2 intersection = vec2_sub(vec2_abs(vec2_sub(b_center, a_center)), vec2_add(a_half_extents, b_half_extents));
                    if (intersection.x > intersection.y)
                    {
                        a->move_velocity.x = 0.0f;

                        if (a->position.x < building->position.x)
                            a->position.x += intersection.x/2.0f;
                        else
                            a->position.x -= intersection.x/2.0f;
                    }
                    else
                    {
                        a->move_velocity.y = 0.0f;

                        if (a->position.y < building->position.y)
                            a->position.y += intersection.y/2.0f;
                        else
                            a->position.y -= intersection.y/2.0f;
                    }
                }
            }

            // Ship-ship collision.
            for (uint32 j = i + 1; j < game_state->ship_count; ++j)
            {
                struct Ship *b = &game_state->ships[j];
                struct AABB b_aabb = aabb_from_transform(b->position, b->size);

                if (aabb_aabb_intersection(a_aabb, b_aabb))
                {
                    vec2 b_center = vec2_div(vec2_add(b_aabb.min, b_aabb.max), 2.0f);
                    vec2 b_half_extents = vec2_div(vec2_sub(b_aabb.max, b_aabb.min), 2.0f);

                    vec2 intersection = vec2_sub(vec2_abs(vec2_sub(b_center, a_center)), vec2_add(a_half_extents, b_half_extents));
                    if (intersection.x > intersection.y)
                    {
                        if (abs_float(a->move_velocity.x) > abs_float(b->move_velocity.x))
                            a->move_velocity.x = 0.0f;
                        else
                            b->move_velocity.x = 0.0f;

                        if (a->position.x < b->position.x)
                        {
                            a->position.x += intersection.x/2.0f;
                            b->position.x -= intersection.x/2.0f;
                        }
                        else
                        {
                            a->position.x -= intersection.x/2.0f;
                            b->position.x += intersection.x/2.0f;
                        }
                    }
                    else
                    {
                        if (abs_float(a->move_velocity.y) > abs_float(b->move_velocity.y))
                            a->move_velocity.y = 0.0f;
                        else
                            b->move_velocity.y = 0.0f;

                        if (a->position.y < b->position.y)
                        {
                            a->position.y += intersection.y/2.0f;
                            b->position.y -= intersection.y/2.0f;
                        }
                        else
                        {
                            a->position.y -= intersection.y/2.0f;
                            b->position.y += intersection.y/2.0f;
                        }
                    }
                }
            }
        }
    }
}