|
|
|
@ -20,86 +20,133 @@ import java.util.Set;
|
|
|
|
|
*
|
|
|
|
|
* @author ASDV2
|
|
|
|
|
*/
|
|
|
|
|
public class NormalizeDatabase {
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
* Finds the closure of a set of attributes given a set of FDs of a relation R
|
|
|
|
|
*
|
|
|
|
|
* @param attributes attributes to find their closure
|
|
|
|
|
* @param fds set of FDs of relation R
|
|
|
|
|
* @return the closure of the parameter attributes.
|
|
|
|
|
*/
|
|
|
|
|
public static String closure(String attributes, ArrayList<FD> fds)
|
|
|
|
|
public class NormalizeDatabase
|
|
|
|
|
{
|
|
|
|
|
/**Finds the closure of a set of attributes given a set of FDs of a relation R
|
|
|
|
|
*
|
|
|
|
|
* @param attributes attributes to find their closure
|
|
|
|
|
* @param fds set of FDs of relation R
|
|
|
|
|
* @return the closure of the parameter attributes.
|
|
|
|
|
*/
|
|
|
|
|
public static String closure(String attributes, ArrayList<FD> fds )
|
|
|
|
|
{
|
|
|
|
|
attributes = attributes.toUpperCase();
|
|
|
|
|
String closurePrevious = attributes;
|
|
|
|
|
for (int j = 0; j < fds.size(); ++j)
|
|
|
|
|
{
|
|
|
|
|
FD capitalsFD = new FD(fds.get(j).getLhs().toUpperCase(),
|
|
|
|
|
fds.get(j).getRhs().toUpperCase());
|
|
|
|
|
fds.set(j, capitalsFD);
|
|
|
|
|
}
|
|
|
|
|
// 1. Set x+ = x
|
|
|
|
|
String closure = attributes;
|
|
|
|
|
for (int i = 0; i < fds.size(); ++i) {
|
|
|
|
|
String closurePreveious = attributes;
|
|
|
|
|
// 2. Starting with x+ apply each FD xF —> y in F where
|
|
|
|
|
// xF belongs in closure x+ but but the rhs y is not already in x+, to find determined
|
|
|
|
|
// attributes y
|
|
|
|
|
// 3. x+ = x+ U y
|
|
|
|
|
|
|
|
|
|
if (closure.contains(fds.get(i).getRhs())) {
|
|
|
|
|
continue;
|
|
|
|
|
while (true)
|
|
|
|
|
{
|
|
|
|
|
|
|
|
|
|
for (int i = 0; i < fds.size(); ++i)
|
|
|
|
|
{
|
|
|
|
|
if (closure.contains(fds.get(i).getRhs()))
|
|
|
|
|
continue;
|
|
|
|
|
// if the left hand side of the FD is contained in the closure
|
|
|
|
|
// then add to the closure the RHS of the FD
|
|
|
|
|
if (closure.contains(fds.get(i).getLhs()))
|
|
|
|
|
closure += fds.get(i).getRhs();
|
|
|
|
|
}
|
|
|
|
|
FD capitalFD = new FD(fds.get(i).getLhs().toUpperCase(),
|
|
|
|
|
fds.get(i).getRhs().toUpperCase());
|
|
|
|
|
}
|
|
|
|
|
//1. Set x+ = x
|
|
|
|
|
//2. Starting with x+ apply each FD xF —> y in F where
|
|
|
|
|
//xF belongs in closure x+, but whre the rhs y is not already in the closure x+
|
|
|
|
|
//to find the determined attribute
|
|
|
|
|
//3. x+ = x+ U y
|
|
|
|
|
while (true) {
|
|
|
|
|
for (int i = 0; i < fds.size(); ++i) {
|
|
|
|
|
//the LHS of the FD is contained in the closure
|
|
|
|
|
//then add to the closure the RHS of the FD
|
|
|
|
|
if (attributes.contains(fds.get(i).getLhs())) {
|
|
|
|
|
attributes += fds.get(i).getRhs();
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
if (closurePrevious.equals(closure)) {
|
|
|
|
|
if (closurePreveious.equals(closure))
|
|
|
|
|
break;
|
|
|
|
|
} else {
|
|
|
|
|
closurePrevious = closure;
|
|
|
|
|
}
|
|
|
|
|
else
|
|
|
|
|
closurePreveious = closure;
|
|
|
|
|
}
|
|
|
|
|
//4, If y not empty go to (2)
|
|
|
|
|
//5. Return x+
|
|
|
|
|
|
|
|
|
|
// 4, If y not empty goto (2)
|
|
|
|
|
// 5. Return x+
|
|
|
|
|
return closure;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
}
|
|
|
|
|
/**
|
|
|
|
|
* Eliminates redundant attributes from the LHS of each FD of a set of FDs given as parameters.
|
|
|
|
|
* Eliminates redundant attributes from the LHS of each FD of a set of FDs
|
|
|
|
|
* given as parameters.
|
|
|
|
|
*
|
|
|
|
|
* @param fds the set of FDs to eliminate the redundancy
|
|
|
|
|
* @return and ArrayList with no redundancy on LHS of each FD.
|
|
|
|
|
*/
|
|
|
|
|
public static ArrayList<FD> eliminateRedundantAttributes(ArrayList<FD> fds)
|
|
|
|
|
{
|
|
|
|
|
return null;
|
|
|
|
|
for (int j = 0; j < fds.size(); ++j)
|
|
|
|
|
{
|
|
|
|
|
int s = fds.get(j).getLhs().length();
|
|
|
|
|
if (s < 2)
|
|
|
|
|
{
|
|
|
|
|
continue;
|
|
|
|
|
}
|
|
|
|
|
else
|
|
|
|
|
{
|
|
|
|
|
String fl = fds.get(j).getLhs().substring(0);
|
|
|
|
|
ArrayList<FD> fFD = new ArrayList<FD>();
|
|
|
|
|
String s1 = " ";
|
|
|
|
|
if (fds.get(j).getLhs().length() == 2)
|
|
|
|
|
{
|
|
|
|
|
|
|
|
|
|
s1 = fds.get(j).getLhs().substring(1);
|
|
|
|
|
fFD.add(new FD (fds.get(j).getLhs().substring(1), fds.get(j).getLhs()));
|
|
|
|
|
System.out.println("closure " + closure(s1, fds));
|
|
|
|
|
System.out.println("Attribute " + s1);
|
|
|
|
|
System.out.println("final (removed " + fFD);
|
|
|
|
|
}
|
|
|
|
|
// else if (fds.get(j).getLhs().charAt(1) == 3)
|
|
|
|
|
// {
|
|
|
|
|
// lFD.add(fds.get(j).getLhs().charAt(1));
|
|
|
|
|
// lFD.add(fds.get(j).getLhs().charAt(2));
|
|
|
|
|
// }
|
|
|
|
|
// else if (fds.get(j).getLhs().charAt(1) == 4)
|
|
|
|
|
// {
|
|
|
|
|
// lFD.add(fds.get(j).getLhs().charAt(1));
|
|
|
|
|
// lFD.add(fds.get(j).getLhs().charAt(2));
|
|
|
|
|
// lFD.add(fds.get(j).getLhs().charAt(3));
|
|
|
|
|
// }
|
|
|
|
|
if (closure(s1, fds).contains(fl))
|
|
|
|
|
{
|
|
|
|
|
return fFD;
|
|
|
|
|
}
|
|
|
|
|
else
|
|
|
|
|
{
|
|
|
|
|
return fds;
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
return null;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
public static void main(String[] args)
|
|
|
|
|
{
|
|
|
|
|
ArrayList<FD> fds = new ArrayList<FD>();
|
|
|
|
|
FD fd = new FD("a", "bc");
|
|
|
|
|
FD fd = new FD("a", "BC");
|
|
|
|
|
FD[] fdDecomposed = fd.decomposeRightHandSide();
|
|
|
|
|
for (int i = 0; i < fdDecomposed.length; ++i) {
|
|
|
|
|
fds.add(new FD(fdDecomposed[i].getLhs(), fdDecomposed[i].getRhs()));
|
|
|
|
|
for (int i = 0; i < fdDecomposed.length; ++i)
|
|
|
|
|
{
|
|
|
|
|
fds.add( new FD(fdDecomposed[i].getLhs(), fdDecomposed[i].getRhs()));
|
|
|
|
|
}
|
|
|
|
|
fds.add(new FD("a", "bc"));
|
|
|
|
|
fds.add(new FD("b", "c"));
|
|
|
|
|
|
|
|
|
|
fds.add(new FD("B", "C"));
|
|
|
|
|
fds.add(new FD("AB", "B"));
|
|
|
|
|
fds.add(new FD("C", "A"));
|
|
|
|
|
System.out.println(fds);
|
|
|
|
|
System.out.println(closure("ac", fds));
|
|
|
|
|
|
|
|
|
|
System.out.println(closure("b", fds));
|
|
|
|
|
System.out.println(eliminateRedundantAttributes(fds));
|
|
|
|
|
/* TEST it with
|
|
|
|
|
Let F1 = {1. A -> BC
|
|
|
|
|
2. B -> C,
|
|
|
|
|
3. AB -> D }.
|
|
|
|
|
Attribute B is extraneous in FD 3 AB -> D
|
|
|
|
|
|
|
|
|
|
*/
|
|
|
|
|
/*
|
|
|
|
|
*/
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
/*
|
|
|
|
|
F2 = { 1. AB -> C,
|
|
|
|
|
2. C -> A,
|
|
|
|
|
3. BC -> D,
|
|
|
|
@ -111,6 +158,6 @@ public class NormalizeDatabase {
|
|
|
|
|
9. CG -> D,
|
|
|
|
|
10. CE -> A,
|
|
|
|
|
11. CE -> G}
|
|
|
|
|
*/
|
|
|
|
|
*/
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|