Problem: Gosha is hunting. His goal is to catch as many Pokemons as possible. Gosha has a Poke Balls and b Ultra Balls. There are n Pokemons. They are numbered 1 through n. Gosha knows that if he throws a Poke Ball at the i-th Pokemon he catches it with probability pi. If he throws an Ultra Ball at the i-th Pokemon he catches it with probability ui. He can throw at most one Ball of each type at any Pokemon.

The hunting proceeds as follows: at first, Gosha chooses no more than a Pokemons at which he will throw Poke Balls and no more than b Pokemons at which he will throw Ultra Balls. After that, he throws the chosen Balls at the chosen Pokemons. If he throws both Ultra Ball and Poke Ball at some Pokemon, he is caught if and only if he is caught by any of these Balls. The outcome of a throw doesn't depend on the other throws.

Gosha would like to know what is the expected number of the Pokemons he catches if he acts in an optimal way. In other words, he would like to know the maximum possible expected number of Pokemons can catch.

Input

The first line contains three integers n, a and b (2 ≤ n ≤ 2000, 0 ≤ a, b ≤ n) — the number of Pokemons, the number of Poke Balls and the number of Ultra Balls.

The second line contains n real values p1, p2, ..., pn (0 ≤ pi ≤ 1), where pi is the probability of catching the i-th Pokemon if Gosha throws a Poke Ball to it.

The third line contains n real values u1, u2, ..., un (0 ≤ ui ≤ 1), where ui is the probability of catching the i-th Pokemon if Gosha throws an Ultra Ball to it.

All the probabilities are given with exactly three digits after the decimal separator.

Output

Print the maximum possible expected number of Pokemons Gosha can catch. The answer is considered correct if it's absolute or relative error doesn't exceed 10 - 4.

Examples

Input

3 2 2
1.000 0.000 0.500
0.000 1.000 0.500


Output

2.75


Input

4 1 3
0.100 0.500 0.500 0.600
0.100 0.500 0.900 0.400


Output

2.16


Input

3 2 0
0.412 0.198 0.599
0.612 0.987 0.443


Output

1.011

Solution (in JAVA):

Solution:

import java.io.*;
import java.math.*;
import java.util.*;

public class Main {

	InputReader in;
	PrintWriter out;

	Main() throws IOException {
		in = new InputReader(System.in);
		out = new PrintWriter(System.out);
		// in = new InputReader(new FileInputStream("input_.txt"));
		// out = new PrintWriter(new File("output_.txt"));
		solve();
		out.close();
	}

	public static void main(String args[]) {
		new Thread(null, new Runnable() {
			public void run() {
				try {
					new Main();
				} catch (Exception e) {
					e.printStackTrace();
				}
			}
		}, "1", 1 << 26).start();
	}

	// --------------------My Code Starts Here----------------------
	long mod = (long) 1e9 + 7;
	double eps = 1e-5;

	public void solve() throws IOException {
		int n = in.nextInt();
		int A = in.nextInt();
		int B = in.nextInt();
		double u[] = new double[n];
		double p[] = new double[n];
		int ptr = 0;
		for (String s : in.nextLine().split(" ")) {
			u[ptr++] = Double.parseDouble(s);
		}
		ptr = 0;
		for (String s : in.nextLine().split(" ")) {
			p[ptr++] = Double.parseDouble(s);
		}
		int N = n + 5;
		int src = n + 1;
		int nodeA = n + 2;
		int nodeB = n + 3;
		int sink = n + 4;
		List<Edge> graph[] = new List[N];
		for (int i = 0; i < N; i++) {
			graph[i] = new ArrayList<>();
		}
		for (int i = 0; i < n; i++) {
			addEdge(graph, nodeA, i, 1, (int)(-u[i]*(1e6)));
			addEdge(graph, nodeB, i, 1, (int)(-p[i]*(1e6)));
			addEdge(graph, i, sink, 1, 0);
			addEdge(graph, i, sink, 1, (int)(u[i]*p[i]*(1e6)));
		}
		addEdge(graph, src, nodeA, A, 0);
		addEdge(graph, src, nodeB, B, 0);
		double ans=-minCostFlow(graph, src, sink, (int)1e6)[1]/1e6;
		out.printf("%.8f\n", ans);
	}
	// ---------------------My Code Ends Here----------------------

	static class Edge {
	    int to, f, cap, cost, rev;

	    Edge(int v, int cap, int cost, int rev) {
	      this.to = v;
	      this.cap = cap;
	      this.cost = cost;
	      this.rev = rev;
	    }
	  }

	  public static List<Edge>[] createGraph(int n) {
	    List<Edge>[] graph = new List[n];
	    for (int i = 0; i < n; i++)
	      graph[i] = new ArrayList<Edge>();
	    return graph;
	  }

	  public static void addEdge(List<Edge>[] graph, int s, int t, int cap, int cost) {
	    graph[s].add(new Edge(t, cap, cost, graph[t].size()));
	    graph[t].add(new Edge(s, 0, -cost, graph[s].size() - 1));
	  }

	  static void bellmanFord(List<Edge>[] graph, int s, int[] dist, int[] prevnode, int[] prevedge, int[] curflow) {
	    int n = graph.length;
	    Arrays.fill(dist, 0, n, Integer.MAX_VALUE);
	    dist[s] = 0;
	    curflow[s] = Integer.MAX_VALUE;
	    boolean[] inqueue = new boolean[n];
	    int[] q = new int[n];
	    int qt = 0;
	    q[qt++] = s;
	    for (int qh = 0; (qh - qt) % n != 0; qh++) {
	      int u = q[qh % n];
	      inqueue[u] = false;
	      for (int i = 0; i < graph[u].size(); i++) {
	        Edge e = graph[u].get(i);
	        if (e.f >= e.cap)
	          continue;
	        int v = e.to;
	        int ndist = dist[u] + e.cost;
	        if (dist[v] > ndist) {
	          dist[v] = ndist;
	          prevnode[v] = u;
	          prevedge[v] = i;
	          curflow[v] = Math.min(curflow[u], e.cap - e.f);
	          if (!inqueue[v]) {
	            inqueue[v] = true;
	            q[qt++ % n] = v;
	          }
	        }
	      }
	    }
	  }

	  public static int[] minCostFlow(List<Edge>[] graph, int s, int t, int maxf) {
	    int n = graph.length;
	    int[] dist = new int[n];
	    int[] curflow = new int[n];
	    int[] prevedge = new int[n];
	    int[] prevnode = new int[n];

	    int flow = 0;
	    int flowCost = 0;
	    while (flow < maxf) {
	      bellmanFord(graph, s, dist, prevnode, prevedge, curflow);
	      if (dist[t] == Integer.MAX_VALUE)
	        break;
	      int df = Math.min(curflow[t], maxf - flow);
	      flow += df;
	      for (int v = t; v != s; v = prevnode[v]) {
	        Edge e = graph[prevnode[v]].get(prevedge[v]);
	        e.f += df;
	        graph[v].get(e.rev).f -= df;
	        flowCost += df * e.cost;
	      }
	    }
	    return new int[]{flow, flowCost};
	  }
	static long modulo(long a, long b, long c) {
		long x = 1;
		long y = a;
		while (b > 0) {
			if (b % 2 == 1) {
				x = (x * y) % c;
			}
			y = (y * y) % c; // squaring the base
			b /= 2;
		}
		return x % c;
	}

	static class Pair<U extends Comparable<U>, V extends Comparable<V>> implements Comparable<Pair<U, V>> {
		public final U u;
		public final V v;

		public Pair(U u, V v) {
			this.u = u;
			this.v = v;
		}

		public int hashCode() {
			return (u == null ? 0 : u.hashCode() * 31) + (v == null ? 0 : v.hashCode());
		}

		public boolean equals(Object o) {
			if (this == o)
				return true;
			if (o == null || getClass() != o.getClass())
				return false;
			Pair<U, V> p = (Pair<U, V>) o;
			return (u == null ? p.u == null : u.equals(p.u)) && (v == null ? p.v == null : v.equals(p.v));
		}

		public int compareTo(Pair<U, V> b) {
			int cmpU = u.compareTo(b.u);
			return cmpU != 0 ? cmpU : v.compareTo(b.v);
		}

	}

	public static void debug(Object... o) {
		System.out.println(Arrays.deepToString(o));
	}

	static final class InputReader {
		private final InputStream stream;
		private final byte[] buf = new byte[1024];
		private int curChar;
		private int numChars;

		public InputReader(InputStream stream) {
			this.stream = stream;
		}

		private int read() throws IOException {
			if (curChar >= numChars) {
				curChar = 0;
				numChars = stream.read(buf);
				if (numChars <= 0)
					return -1;
			}
			return buf[curChar++];
		}

		public final int nextInt() throws IOException {
			return (int) nextLong();
		}

		public final long nextLong() throws IOException {
			int c = read();
			while (isSpaceChar(c)) {
				c = read();
				if (c == -1)
					throw new IOException();
			}
			boolean negative = false;
			if (c == '-') {
				negative = true;
				c = read();
			}
			long res = 0;
			do {
				if (c < '0' || c > '9')
					throw new InputMismatchException();
				res *= 10;
				res += (c - '0');
				c = read();
			} while (!isSpaceChar(c));
			return negative ? (-res) : (res);
		}

		public final int[] readIntBrray(int size) throws IOException {
			int[] arr = new int[size];
			for (int i = 0; i < size; i++)
				arr[i] = nextInt();
			return arr;
		}

		public final String next() throws IOException {
			int c = read();
			while (isSpaceChar(c))
				c = read();
			StringBuilder res = new StringBuilder();
			do {
				res.append((char) c);
				c = read();
			} while (!isSpaceChar(c));
			return res.toString();
		}

		public final String nextLine() throws IOException {
			int c = read();
			while (isSpaceChar(c))
				c = read();
			StringBuilder res = new StringBuilder();
			do {
				res.append((char) c);
				c = read();
			} while (c != '\n' && c != -1);
			return res.toString();
		}

		private boolean isSpaceChar(int c) {
			return c == ' ' || c == '\n' || c == '\r' || c == '\t' || c == -1;
		}
	}
}