zoukankan      html  css  js  c++  java
  • 字典树变形 A

    A - Gaby And Addition

     Gym - 101466A 

    这个题目是一个字典树的变形,还是很难想到的。

    因为这题目每一位都是独立的,不会进位,这个和01字典树求最大的异或和是不是很像。

    知道这个了,就还比较好写了,不过要注意数组越界和超时问题。

    #include <cstdio>
    #include <cstring>
    #include <algorithm>
    #include <iostream>
    #include <algorithm>
    #include <cstdlib>
    #include <vector>
    #include <stack>
    #include <map>
    #include <string>
    #define inf 0x3f3f3f3f
    #define inf64 0x3f3f3f3f3f3f3f3f
    using namespace std;
    typedef long long ll;
    const int maxn = 1e6 + 10;
    ll val[maxn * 20];
    int trie[maxn * 20][10], tot;
    ll f[20];
    void init() {
    	tot = 1;
    	memset(trie[0], 0, sizeof(trie[0]));
    	f[0] = 1;
    	for (int i = 1; i <= 18; i++) f[i] = f[i - 1] * 10;
    }
     
    void insert(ll x) {
    	int u = 0;
    	// printf("x=%lld
    ", x);
    	for (int i = 18; i >= 0; i--) {
    		ll v = (x / f[i]) % 10;
    		// printf("i=%d v=%lld
    ", i, v);
    		if (trie[u][v] == 0) {
    			memset(trie[tot], 0, sizeof(trie[tot]));
    			val[tot] = 0;
    			trie[u][v] = tot++;
    		}
    		// printf("u=%d v=%lld
    ", u, v);
    		u = trie[u][v];
    	}
    	val[u] = x;
    }
     
    ll query_max(ll x) {
    	int u = 0;
    	for (int i = 18; i >= 0; i--) {
    		ll v = (x / f[i]) % 10;
    		bool flag = 0;
    		for (int j = 9 - v; j >= 0; j--) {
    			if (trie[u][j]) {
    				flag = 1;
    				u = trie[u][j];
    				break;
    			}
    		}
    		if (flag == 0) {
    			for (int j = 9; j >= 9 - v + 1; j--) {
    				if (trie[u][j]) {
    					u = trie[u][j];
    					break;
    				}
    			}
    		}
    	}
    	return val[u];
    }
     
    ll query_min(ll x) {
    	// printf("x=%lld
    ", x);
    	int u = 0;
    	for (int i = 18; i >= 0; i--) {
    		ll v = (x / f[i]) % 10;
    		// printf("i=%d v=%lld
    ", i, v);
    		bool flag = 0;
    		for (int j = 9 - v + 1; j <= 9; j++) {
    			// printf("www u=%d v=%lld j=%d
    ", u, v,j);
    			if (trie[u][j]) {
    				u = trie[u][j];
    				// printf("j=%d
    ", j);
    				flag = 1;
    				break;
    			}
    		}
    		if (flag == 0) {
    			for (int j = 0; j <= 9 - v; j++) {
    				if (trie[u][j]) {
    					u = trie[u][j];
    					break;
    				}
    			}
    		}
    	}
    	// printf("val=%lld
    ", val[u]);
    	return val[u];
    }
     
    ll a[maxn];
     
    ll check(ll a, ll b) {
    	ll ans = 0;
    	// printf("a=%lld b=%lld
    ", a, b);
    	for (int i = 18; i >= 0; i--) {
    		ans = ans * 10 + (a / f[i] % 10 + b / f[i] % 10) % 10;
    	}
    	return ans;
    }
     
    int main() {
    	int n;
    	init();
    	scanf("%d", &n);
    	ll maxs = 0, mins = inf64;
    	for (int i = 1; i <= n; i++) {
    		scanf("%lld", &a[i]);
    		if(i!=1)
    		{
    			ll res1 = query_max(a[i]);
    			ll res2 = query_min(a[i]);
    			maxs = max(maxs, check(a[i], res1));
    			mins = min(mins, check(a[i], res2));
    		}
    		insert(a[i]);
    	}
    	printf("%lld %lld
    ", mins, maxs);
    	return 0;
    }
    

      

  • 相关阅读:
    NoHttp开源Android网络框架1.0.0之架构分析
    3种浏览器性能測试
    自己定义控件-画板,橡皮擦,刮刮乐
    android优化 清除无效代码 UCDetector
    iOS推送 (百度推送)
    C#中的协变OUT和逆变
    使用反射构造对象实例并动态调用方法
    用反射获取构造函数带参数的实例对象
    自己实现一个IOC(控制翻转,DI依赖注入)容器
    func 和action 委托的使用
  • 原文地址:https://www.cnblogs.com/EchoZQN/p/11342521.html
Copyright © 2011-2022 走看看