BZOJ 4472 vendedor 题 解

título

T un vendedor a una serie de pequeños pueblos para vender los productos básicos, ya que la zona es montañas inaccesibles, cualquier posible después de todo, sólo hay una ruta entre las dos ciudades otras ciudades. Pequeño T puede estimar con precisión la red en todas las ciudades para quedarse. Estas ganancias netas pueden ser negativos, es decir, los beneficios de mercancías vender no vale la pena el costo. Debido a las malas carreteras, pequeña T a través de cada ciudad necesita para mantenerse, independientemente de la red en el número de lugares para alojarse en todas las ciudades, porque muchas veces el costo del medidor no está cargada, pero cada pueblo a la demanda de los productos básicos es también una pequeña camiseta relativamente fijo, el tiempo de residencia después saturado. Con el fin de fortalecer el orden público en cada ciudad, hay reglas estrictas para el mayor número de extranjeros estancia. Usted ayuda a diseñar un pequeño devuelve t el mayor programa del viaje, es decir, desde el hogar, la estancia en cada ciudad después finalmente regresó a su ciudad natal de programa de viajes. Su programa acaba de emitir el máximo beneficio, y la solución óptima es única. Programa no incluye los detalles de la ruta, el mismo programa estándar se selecciona a través de la ciudad y que permanecen igual. Debido a la gira cancelada es también un esquema, los ingresos máximos no serán negativos. T pequeño pueblo natal en la utilidad neta es cero, porque el hogar es una pequeña ciudad natal local del T ciertamente no limitar el número de residencia.

Formato de entrada

La primera línea de entrada es un número entero positivo \ (n-n- (. 5 <= <= 100,000) \) , que representa el número de ciudades. Poblaciones con \ (1 \) a \ (n \) el número de nombres. Pequeña ciudad natal llamado T \ (1 \) . La segunda y tercera filas separadas por un espacio que contiene (n-1 \) \ número entero, la segunda fila \ (I \) número representa la ciudad \ (i + 1 \) estancia neto . La tercera línea de \ (i \) número representa la ciudad \ (i + 1 \) el número máximo de disposiciones estancias. Todas las estancias son no menos que el número máximo de \ (2 \) . El siguiente \ (n-1 \) líneas cada uno para dos 1 \ (n- \) número entero positivo \ (X \) , \ (Y \) , separadas por un espacio en el medio, representar \ (X \ ) , \ (el y- \) que hay entre un camino de dos vías sin pasar por otras ciudades. Los datos de entrada para asegurar que todos los pueblos están conectados.

Formato de salida

Hay dos líneas de salida, la primera línea contiene un número natural que representa el recorrido máximo recorrido beneficio. Si el programa único, en la segunda línea de la salida "solución es única", o "no es solución única" en la segunda línea de salida.

Ejemplo de entrada

9
-3 -4 2 4 -2 3 4 6
4 4 2 2 2 2 2 2 
1 2
1 3
1 4
2 5
2 6
3 7
4 8 
4 9

Ejemplo de salida

9
solution is unique

la interpretación de la muestra

Mejor ruta ciudad incluye 1,2, 4, 5, 9

solución del problema

Después de todo sólo hay una posible ruta entre otras dos localidades de la ciudad , lo que indica que este debe ser un árbol

En primer lugar pidió

Esta cuestión es, obviamente, moviendo reglas del árbol, pero añadió una condición de restricción de que el número máximo de estancia, en la forma de un árbol cuando la acción reguladora de Lenovo, de hecho, el mayor número de estancia y el número de sub-árboles puede acceder a una relación.

La figura muestra un procedimiento DFS, en el que todos los números 2,3,4,5,6 subárbol, si los subárboles como un punto, entonces el proceso pasa nodo DFS es

[1] 2 [1] 2 [1] 4 [1] 5 [1] 6 [1]

Tenga en cuenta que la raíz de los cuales 1, ha habido seis veces en este problema es dejar de seis veces, mientras que el No. 1 nodo tiene cinco sub-árboles se pueden encontrar, si el número máximo de estancias nodo i \ (límite [los ejes X] \) , la DFS acceso hasta \ (límite [x] -1 \ ) subárbol

Estas diferentes sub-árboles contribuyen a la raíz de dp, ciertamente tenemos que elegir uno de los más grandes, por lo que se produjo la orden, antes de la elección en la que el (límite [x] -1 \) \ nodo raíz sub-árbol para actualizar el valor de los árboles dp.

Tenga en cuenta que, \ (límite [X] -1 \) también existe la mayor caso que el número de subárboles, así que cuando la operación real para tomar \ (límite [x] \) y el número mínimo de sub-palabras como la raíz actualizado el número de árboles, debido al resultado neto puede ser negativo, por lo que la actualización cuando se encontró a ser negativo puede ser detenida de inmediato.

Así que atraviesan el subárbol (ordenados) cuando las condiciones

soni < min(limit[root] - 1, sontot) && dp[sonn[soni + 1]] >= 0

Entre ellos, sonies la variable de bucle en el bucle subárbol corriente a través de (nota que de vez en número de nodo sub-root tiempo), rootcomo un número de nodo raíz, sontotel número de sub-árbol, sonnmatriz contiene el número de nodo raíz subárbol, sonn[soni+1]para este subárbol ciclo número (en la circulación debido a incremento soni 1)

También hay una condición

Hogar de una pequeña T, por supuesto, no se detuvo a limitar el número de

Esa es la raíz de todo el árbol número ilimitado de veces, sólo tiene que antes de la raíz DFS limitvalor se puede asignar al infinito

La segunda pregunta

Obviamente, el programa es el primer aspecto único en la base de su subárbol, si hay alguna actualización de un valor de DP raíz subárbol de los programas no es única, la raíz del programa no es claramente único.

Además, existe un programa de raíz subárbol programa único pero selecto sub-árbol no es el único caso.

Cuando se atraviesa el subárbol, el valor único si el nodo raíz subárbol para seleccionar programas y subárbol programa es único valor de un OR (siempre y cuando una es verdadera, el resultado es verdadero), el resultado obtenido es el árbol programa es único, el resultado final puede ser.

Entonces, ¿cómo determinar si el nodo raíz sub-árbol seleccionado del único programa de la misma, hay dos casos:

  1. No es la única causa del mismo valor

Suponiendo que la fila sub-árbol después de una secuencia de valor dp buena 10 9 8 7 6 6 5 4 3 2 1, y sólo se puede elegir 5 ( limit= 6), es obvio que elija 10 9 8 7 6, pero mira de cerca, se encuentra que hay una idéntica 6, entonces no puedo abandonar los primeros 6 para seleccionar el segundo 6? por supuesto que puede, entonces esto tendría dos opciones ( [10] [9] [8] [7] [6] 6 5 4 3 2 1y [10] [9] [8] [7] 6 [6] 5 4 3 2 1), este caso no es necesario prestar atención a limitlos valores límite, ya no hay más que una opción, que es abandonar una reelección una , el número de sub-árbol utiliza para actualizar sin cambios.

  1. dp valor de 0 no es única debido a la

Suponiendo que la fila sub-árbol después de una secuencia de valor dp buena 10 9 8 7 6 0, y sólo se puede elegir cinco (límite es 6), se puede elegir 10 9 8 7 6, también puede seleccionar 10 9 8 7 6 0, actualizar el valor de estos dos programas son los mismos, las necesidades de esta situación Tenga en cuenta que limitel valor límite, incluso si el limitvalor es 0, si se selecciona, será más tiempo para estar aunque los datos un poco de agua, además de pro-prueba sin limitvalores límite pueden ser una .

El evento ambos casos, estos árboles directamente si el programa sólo puede asignar cierto

código

#include <algorithm>
#include <cstdio>
#include <cstring>
using namespace std;
const int N = 100000;
struct edge {
    int i, next;
} edges[2 * N + 5];
int head[N + 5], tot, n, w[N + 5], limit[N + 5], dp[N + 5], ansn[N + 5],sonn[N + 5];
void add(int u, int v) {
    edges[++tot].i = v;
    edges[tot].next = head[u];
    head[u] = tot;
}
bool cmp(int a, int b) { return dp[a] > dp[b]; }
void dfs(int root, int f) {
    dp[root] = w[root];
    int sontot = 0, soni = 0;
    for (int i = head[root]; i; i = edges[i].next)
        if (edges[i].i != f) dfs(edges[i].i, root);
    for (int i = head[root]; i; i = edges[i].next)
        if (edges[i].i != f) sonn[++sontot] = edges[i].i;
    sort(sonn + 1, sonn + 1 + sontot, cmp);
    while (soni < min(limit[root] - 1, sontot) && dp[sonn[soni + 1]] >= 0)
        dp[root] += dp[sonn[++soni]], ansn[root] |= ansn[sonn[soni]];//按位或
    if (soni < sontot && soni > 0 && dp[sonn[soni]] == dp[sonn[soni + 1]] || dp[sonn[soni]] == 0 && soni > 0 && soni <= limit[root] - 1)//两种情况,注意边界
        ansn[root] = 1;
}
int main() {
    scanf("%d", &n);
    for (int i = 1; i < n; i++) scanf("%d", &w[i + 1]);
    for (int i = 1; i < n; i++) scanf("%d", &limit[i + 1]);
    for (int i = 1; i < n; i++) {
        int u, v;
        scanf("%d%d", &u, &v);
        add(u, v);
        add(v, u);
    }
    limit[1] = n + 1;//在家乡没有停留限制
    dfs(1, 0);
    printf("%d\n%s", dp[1], ansn[1] ? "solution is not unique" : "solution is unique");
    return 0;
}

Supongo que te gusta

Origin www.cnblogs.com/youxam/p/bzoj4472.html
Recomendado
Clasificación