求最小依赖集java代码

最小依赖集代码,step3()只有一次遍历左边集,所以存在问题,但将step2()放在step3()前面,则掩饰了它的问题,程序可以得出正常结果。

代码有点稀烂,应该先提取个getClosure()求属性闭包的方法,这样可以减少代码量。还有BuilderString在此处完全体现不出作用,建议改成String。

 

package 最小化依赖集;

import java.util.LinkedList;
import java.util.Scanner;

/**
 *
 * @author Administrator
 */
public class NewClass {
    static LinkedList<Depen> list = new LinkedList();

    static class Depen {
        StringBuilder begin;
        StringBuilder end;

        public Depen(StringBuilder begin, StringBuilder end) {
            this.begin = begin;
            this.end = end;
        }
    }

    public static void main(String[] args) {
        Scanner scan = new Scanner(System.in);
        int num = scan.nextInt();
        for (int i = 0; i < num; i++) {
            Depen dp = new Depen(new StringBuilder(scan.next()), new StringBuilder(scan.next()));
            list.add(dp);
        }
        step1();
        print();
        step2();
        print();
        step3();
        print();
    }

    public static void step1() {                     //右边化为单属性集合
        LinkedList<Depen> save = new LinkedList();
        for (int i = 0; i < list.size(); i++) {
            Depen dp = list.get(i);
            int len = dp.end.length();
            if (len > 1) {
                StringBuilder begin = dp.begin;
                StringBuilder end = dp.end;
                for (int j = 0; j < len; j++) {
                    save.add(new Depen(begin, new StringBuilder(end.charAt(j) + "")));
                }
                list.remove(i);
                i--;
            }
        }
        for (int i = 0; i < save.size(); i++) {
            list.add(save.get(i));
        }
    }

    public static void step2() {                    //去掉多余的依赖

        boolean[] del = new boolean[list.size()];
        for (int i = 0; i < list.size(); i++) {           //去掉第i个试试
            Depen dp = list.get(i);
            StringBuilder save = new StringBuilder(dp.begin);
            boolean[] add = new boolean[list.size()];
            boolean b = false;
            for (int j = 0; j < list.size(); j++) { 
                if (i != j && !add[j] && !del[j]) {
                    if (contains(list.get(j).begin, save)) {
                        save.append(list.get(j).end);
                        add[j] = true;
                        b = true;
                    }
                }
                if (j == list.size() - 1 && b == true) {          //继续遍历
                    j = -1;
                    b=false;
                } else {                       //已经到最后
                    if (contains(list.get(i).end, save)) {
                        del[i] = true;
                        break;        //跳出j循环
                    }
                }
            }
        }
        int count = 0;
        for (int i = 0; i < del.length; i++) {
            if (del[i]) {
                list.remove(i - count);
                count++;
            }
        }

    }

    public static void step3() {
        for (int i = 0; i < list.size(); i++) {
            if(list.get(i).begin.length()==1) continue;
            for (int j = 0; j < list.get(i).begin.length(); j++) {                //假设去掉list.get(i).begin第j个字母
                Depen dp = list.get(i);
                StringBuilder begin = dp.begin;
                StringBuilder sb = new StringBuilder(begin.substring(0, j) + begin.substring(j + 1));
                StringBuilder save = new StringBuilder(sb);
                boolean[] add = new boolean[list.size()];
                boolean b = false;
                for (int k = 0; k < list.size(); k++) {                             //依次扩大闭包
                    if (!add[k]) {                    //初始化未有函数依赖加入闭包 (字符串去掉某个字母后还需要扩展原字符串)                                             
                        if (contains(list.get(k).begin, save)) {
                            save.append(list.get(k).end);
                            add[k] = true;
                            b = true;
                        }
                    }
                    if (b && k == list.size() - 1) {
                        k = -1;
                        b=false;
                    } else {
                        if (contains(dp.end, save)) {
                            list.set(i, new Depen(sb, dp.end));            //可以去掉第j个字母
                            j--;
                            break;
                        }
                    }

                }
            }
            if (list.get(i).begin.length() == 0) {
                list.remove(i);
                i--;
            }
        }

    }

    public static boolean contains(StringBuilder sb1, StringBuilder sb2) {      //sb2 contains sb1?
        for (int i = 0; i < sb1.length(); i++) {
            String s = sb2 + "";
            if (!s.contains(sb1.charAt(i) + "")) {
                return false;
            }
        }
        return true;
    }

    public static void print() {
        System.out.println("-------------------------------");
        for (int i = 0; i < list.size(); i++) {
            Depen dp = list.get(i);
            System.out.println(dp.begin + "->" + dp.end);
        }
    }
}

  • 0
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值