Cod sursa(job #535236)

Utilizator feelshiftFeelshift feelshift Data 16 februarie 2011 21:46:32
Problema Parantezare optima de matrici Scor 100
Compilator cpp Status done
Runda Arhiva educationala Marime 2.01 kb
// http://infoarena.ro/problema/podm
#include <fstream>
#include <algorithm>
using namespace std;

// cu 0x3f3f3f3f - WA pe doua teste
#define INFINITY 99999999999999999LL
#define maxSize 501

int numberOfMatrices;
// pereche (size[i-1],size[i]) reprezinta dimensiunile matricei i
long long size[maxSize];
long long best[maxSize][maxSize];

void read();
void solveAndWrite();

int main() {
	read();
	solveAndWrite();	

	return (0);
}

void read() {
	ifstream in("podm.in");

	in >> numberOfMatrices;

	for(int i=0;i<=numberOfMatrices;i++)
		in >> size[i];

	in.close();
}

void solveAndWrite() {
	ofstream out("podm.out");

	// "diagonala" deasupra diagonalei principale
	// (punctul de pornire al dinamicii)
	for(int i=1;i<=numberOfMatrices-1;i++)
		best[i][i+1] = size[i-1] * size[i] * size[i+1];
	

	// se completeaza toate elementele deasupra diagonalei principale
	// (prima "diagonala" a fost completata anterior), constructia
	// tabloului facandu-se diagonala cu diagonala

	// s reprezinta indicele coloanei de inceput a "diagonalei"
	for(int s=2;s<=numberOfMatrices-1;s++)
		// i ia fiecare linie a "diagonalei" anterioare
		for(int i=1;i<=numberOfMatrices-s;i++) {
			// j reprezinta coloana din "diagonala"
			// (ea se deplaseaza la dreapta pe masura
			// ce i coboara cate un rand)
			int j = i + s;

			// best[i][j] = costul minim de inmultire a matricelor size[i],size[i+1]...size[j]
			best[i][j] = INFINITY;

			// k reprezinta "taietura" in intervalul i,i+1....numberOfMatrices
			// parcurgem toate "taieturile" pentru a gasi solutia optima
			// (minimul dintre cea curenta si cele doua intervale formate
			// de k plus costul unirii lor (produsul matriceal))
			for(int k=i;k<=j-1;k++)
				best[i][j] = min(best[i][j],best[i][k] + best[k+1][j] + size[i-1]*size[k]*size[j]);
		}

	// solutia costruindu-se de la stanga la dreapta
	// costul minim se va gasi in coltul
	// din dreapta sus al tabloului
	out << best[1][numberOfMatrices] << "\n";

	out.close();
}