Cod sursa(job #903345)

Utilizator palcuiealexAlex Palcuie palcuiealex Data 1 martie 2013 20:10:53
Problema Infasuratoare convexa Scor 0
Compilator cpp Status done
Runda Arhiva educationala Marime 3.42 kb
/***************************************************
 * Alex Palcuie
 * Romania
 * alex [dot] palcuie [at] gmail [dot] com
 * http://palcu.blogspot.com/
 * 2013
****************************************************/

#include <vector>
#include <list>
#include <map>
#include <set>
#include <deque>
#include <stack>
#include <queue>
#include <bitset>
#include <algorithm>
#include <utility>
#include <iostream>
#include <cstdio>
#include <cmath>
#include <cstdlib>
#include <ctime>
#include <iterator>
#include <cstring>

using namespace std;

// Defines
#define NAME(n) #n
#define pr(x) db((x), (#x))
#define prv(v,n) dbv((v), (#v), (n))
#define prw(v) dbw((v), (#v))
#define X first
#define Y second
#define pb push_back

// Helpers
template <typename T>
inline void db(const T x, const char * name){
	cerr << name << " = " << x << '\n';
}
template <typename T> inline void dbv(const T * v, const char * name, int n){
	fprintf(stderr, "=== %s ===\n", name);
	for(int i=0; i<n; i++)
		cerr << v[i] << " ";
	cerr << '\n';
}
template <typename T> inline void dbs(T x){
	cerr << x << ' ';
}

template<typename T>
void dbw(const std::vector<T>& t, const char * name){
	fprintf(stderr, "=== %s ===\n", name);
	unsigned n = t.size();
	for(typename std::vector<T>::size_type i=0; i<n; ++i)
		std::cerr << t[i] << ' ';
	cerr << '\n';
}

// Constants
const int N = 1<<10;
const int INF = 0x3f3f3f3f;

// Globals
int nNoduri, val[N], sumePartiale[N];
vector<int> v[N];
bool visit[N];
bool nuInPrimulArbore[N];

// Structs

// Functions
int calcSumePartiale(int nod){
    int sum = val[nod];
    visit[nod] = true;

    /*for(int i=0; i<v[nod].size(); i++)
        printf("%d ", v[nod][i]);
    printf("\n");*/

    for(int i=0; i<v[nod].size(); i++){
        int newNod = v[nod][i];
        if(!visit[newNod]){
            //pr(newNod);
            sum += calcSumePartiale(newNod);
        }
    }
    sumePartiale[nod] = sum;
    return sum;
}

void scadeParinte(int nod, int val, int s[N]){
    s[nod] -= val;
    for(int i=0; i<v[nod].size(); i++){
        int newNod = v[nod][i];
        if(newNod < nod && !nuInPrimulArbore[newNod])
            scadeParinte(newNod, val, s);
    }
}

int solve(int a, int b, int c){
    int sums[N], i;
    vector<int> sol;
    memcpy(sums, sumePartiale, sizeof(sumePartiale));
    int k[] = {a, b, c};

    for(int  j=0; j<3; j++){
        int a = k[j];
        nuInPrimulArbore[a] = true;
        for(i=0; i<v[a].size(); i++)
            if(v[a][i] < a)
                scadeParinte(v[a][i], sums[a], sums);
    }


    sol.pb(sums[1]);sol.pb(sums[a]);sol.pb(sums[b]);sol.pb(sums[c]);
    vector<int>::iterator myMin = min_element(sol.begin(), sol.end());
    vector<int>::iterator myMax = max_element(sol.begin(), sol.end());
    return *myMax - *myMin;
}

int main(){
	#ifndef ONLINE_JUDGE
	freopen("petrica.in","r",stdin);
	freopen("petrica.out","w",stdout);
	#endif

	int i, a, b, j, k;
	scanf("%d", &nNoduri);
	for(i=0; i<nNoduri; i++) scanf("%d", &val[i+1]);
	while(!feof(stdin)){
        scanf("%d %d\n", &a, &b);
        v[a].pb(b);
        v[b].pb(a);
	}

    calcSumePartiale(1);
    //prv(sumePartiale, nNoduri+1);

    int sol = INF; nuInPrimulArbore[1] = true;
    for(i=2; i<=nNoduri-2; i++)
        for(j=i+1; j<=nNoduri-1; j++)
            for(k=j+1; k<=nNoduri; k++){
                sol = min(sol, solve(i,j,k));
                nuInPrimulArbore[i] = nuInPrimulArbore[j] = nuInPrimulArbore[k] = false;
            }

    printf("%d\n", sol);
	return 0;
}