Loading .idea/misc.xml +1 −1 Original line number Diff line number Diff line Loading @@ -3,7 +3,7 @@ <component name="ProjectKey"> <option name="state" value="project://e2804f05-5315-4fc6-a121-c522a6c26470" /> </component> <component name="ProjectRootManager" version="2" languageLevel="JDK_1_8" default="true" project-jdk-name="1.8" project-jdk-type="JavaSDK"> <component name="ProjectRootManager" version="2" languageLevel="JDK_17" default="true" project-jdk-name="17" project-jdk-type="JavaSDK"> <output url="file://$PROJECT_DIR$/out" /> </component> </project> No newline at end of file src/edu/bu/ec504/hw1p1/DistinctCounter.java +32 −21 Original line number Diff line number Diff line package edu.bu.ec504.hw1p1; /** * Attempts to approximate the number of distinct elements seen so far. * AMaintains an approximate count of the number of distinct elements seen so far. */ public abstract class DistinctCounter { // FIELDS final private Byte[] state; /** * The memory associated with the counter. */ protected final FixedBitArray mem; // METHODS Loading @@ -14,48 +18,55 @@ public abstract class DistinctCounter { /** * This constructor cannot be used. */ private DistinctCounter() { state = null; } private DistinctCounter() {mem = null;} /** * Constructs an object backed by a given memory size. * @param stateSize The size of the memory backing, in number of integers. * Constructs an DistinctCounter with a given size of memory. * * @param memBits The number of bits of memory available to the counter. */ public DistinctCounter(int stateSize) { state = new Byte[stateSize]; public DistinctCounter(int memBits) { mem = new FixedBitArray(memBits); } /** * Creates a DistinctCounter object from a given initial state. * @param initialState The output of a call to {@link #currentState()} on some DistinctCounter object. * Sets the memory of this DistinctCounter object to <code>initialMem</code>. * * @param initialMem The memory to set for this object. * It should be in the same format as the output of a call to {@link #currentState()} * for some DistinctCounter object. */ public DistinctCounter(Byte[] initialState) { state = new Byte[initialState.length]; System.arraycopy(initialState, 0, state, 0, initialState.length); public void setMem(FixedBitArray initialMem) { if (mem.len != initialMem.len) throw new IllegalArgumentException( "Trying to set memory with an incompatible argument."); else { // copy initialMem bits to this object mem.bits.clear(); mem.bits.xor(initialMem.bits); } } // ... OPERATIONAL /** * Log a new element that is seen. * Note a new element that is seen. * * @param newElement The element that was seen. */ abstract void saw(String newElement); /** * * @return A guess of the number of distinct elements that were seen. */ abstract Integer numDistinct(); // ... INFORMATIONAL /** * outputs the current state of the DistinctCounter * */ public Byte[] currentState() { return state; } // NESTED CLASSES public static class NotYetImplemented extends RuntimeException { */ final public FixedBitArray currentState() { return mem; } } src/edu/bu/ec504/hw1p1/FixedBitArray.java 0 → 100644 +114 −0 Original line number Diff line number Diff line package edu.bu.ec504.hw1p1; import java.util.BitSet; /** * Implements aan array of bits whose size cannot be changed. */ public class FixedBitArray { // FIELDS /** * The length, in bits, of this array. */ public final int len; /** * The bits stored in this array. */ final BitSet bits; // METHODS /** * Constructs an object that handles <code>theLen</code> bits. * * @param theLen The number of bits that the object can handle. */ public FixedBitArray(int theLen) { len = theLen; bits = new BitSet(len); } public FixedBitArray(byte[] bytes) { len = bytes.length; bits = BitSet.valueOf(bytes); } /** * @param bitIndex The index at which the array is being queried. * @return The bit at the array index <code>bitIndex</code>. */ public boolean get(int bitIndex) { confirmIndex(bitIndex); return bits.get(bitIndex); } /** * Sets the bit at index <code>bitIndex</code> to true. * * @param bitIndex The index to set true. */ public void set(int bitIndex) { confirmIndex(bitIndex); bits.set(bitIndex); } /** * Clears the bit at index <code>bitIndex</code> to true. * * @param bitIndex The index to set true. */ public void clear(int bitIndex) { confirmIndex(bitIndex); bits.clear(bitIndex); } /** * Flips the parity of the bit at index <code>bitIndex</code> * * @param bitIndex The index of the bit in the array to flip. */ public void flip(int bitIndex) { confirmIndex(bitIndex); bits.flip(bitIndex); } /** * @return A byte array corresponding to memory of this object */ public byte[] toByteArray() { rectifyBits(); return bits.toByteArray(); } /** * @param bytes The contents of the new array. * @return A FixedBitArray whose contents are <code>bytes</code> */ static public FixedBitArray valueOf(byte[] bytes) { return new FixedBitArray(bytes); } @Override public String toString() { return "[" + len + " bits]: " + bits.toString(); } /** * Confirms that <code>bitIndex</code> is within the dynamic range of indices * handled by this array, returning normally if confirmation succeeds. * * @param bitIndex The index to check. * @throws ArrayIndexOutOfBoundsException if <bode>bitIndex</bode> is out of * range for this array. */ private void confirmIndex(int bitIndex) { if (bitIndex < 0 || bitIndex >= len) {throw new ArrayIndexOutOfBoundsException(bitIndex);} } /** * Make sure there are no bits outside the dynamic range of the array. */ private void rectifyBits() { bits.set(len, bits.size(), false); } } src/edu/bu/ec504/hw1p1/Main.java +16 −10 Original line number Diff line number Diff line Loading @@ -2,31 +2,37 @@ package edu.bu.ec504.hw1p1; import java.math.BigInteger; import java.util.ArrayList; import java.util.Arrays; import java.util.HashSet; import java.util.List; import java.util.Set; public class Main { // constants static final int stateSize = 10; // the number of bytes in the myDistinctCounter object static final int memSize = 10; // the number of bits backing the counter /** * Run {@link myDistinctCounter} through the test strings provided, and report its results. * @param testStrings The strings to run by the {@link myDistinctCounter}. * Run {@link MyDistinctCounter} through the test strings provided, and report its results. * @param testStrings The strings to run by the {@link MyDistinctCounter}. */ static void test(ArrayList<String> testStrings) { // Show the counter my test strings myDistinctCounter tester = new myDistinctCounter(stateSize); MyDistinctCounter tester = new MyDistinctCounter(memSize); Set<String> verifier = new HashSet<>(); for (String test: testStrings) { tester.saw(test); verifier.add(test); } // Record the counter's state Byte[] savedState = tester.currentState(); System.out.println("Counter state is: "+ Arrays.toString(savedState)); FixedBitArray savedState = tester.currentState(); System.out.println("Counter state is: "+ savedState); // Output the prediction myDistinctCounter newFoo = new myDistinctCounter(savedState); System.out.println("# of distinct strings: "+newFoo.numDistinct()); // Output the guess MyDistinctCounter newFoo = new MyDistinctCounter(memSize); newFoo.setMem(savedState); System.out.println("guessed # of distinct strings: "+newFoo.numDistinct()); System.out.println(" actual # of distinct strings: "+verifier.size()); } /** Loading src/edu/bu/ec504/hw1p1/myDistinctCounter.java→src/edu/bu/ec504/hw1p1/MyDistinctCounter.java +10 −10 Original line number Diff line number Diff line package edu.bu.ec504.hw1p1; public class myDistinctCounter extends DistinctCounter { public class MyDistinctCounter extends DistinctCounter { /** * @inheritDoc */ public myDistinctCounter(int stateSize) { super(stateSize); public MyDistinctCounter(int memBits) { super(memBits); throw new NotYetImplemented(); // replace this with your code! } /** * @inheritDoc */ public myDistinctCounter(Byte[] initialState) { super(initialState); @Override void saw(String newElement) { throw new NotYetImplemented(); // replace this with your code! } Loading @@ -22,15 +22,15 @@ public class myDistinctCounter extends DistinctCounter { * @inheritDoc */ @Override void saw(String newElement) { Integer numDistinct() { throw new NotYetImplemented(); // replace this with your code! } // NESTED CLASSES /** * @inheritDoc * A runtime exception indicating that a method has not yet been implemented. */ @Override Integer numDistinct() { throw new NotYetImplemented(); // replace this with your code! public static class NotYetImplemented extends RuntimeException { } } Loading
.idea/misc.xml +1 −1 Original line number Diff line number Diff line Loading @@ -3,7 +3,7 @@ <component name="ProjectKey"> <option name="state" value="project://e2804f05-5315-4fc6-a121-c522a6c26470" /> </component> <component name="ProjectRootManager" version="2" languageLevel="JDK_1_8" default="true" project-jdk-name="1.8" project-jdk-type="JavaSDK"> <component name="ProjectRootManager" version="2" languageLevel="JDK_17" default="true" project-jdk-name="17" project-jdk-type="JavaSDK"> <output url="file://$PROJECT_DIR$/out" /> </component> </project> No newline at end of file
src/edu/bu/ec504/hw1p1/DistinctCounter.java +32 −21 Original line number Diff line number Diff line package edu.bu.ec504.hw1p1; /** * Attempts to approximate the number of distinct elements seen so far. * AMaintains an approximate count of the number of distinct elements seen so far. */ public abstract class DistinctCounter { // FIELDS final private Byte[] state; /** * The memory associated with the counter. */ protected final FixedBitArray mem; // METHODS Loading @@ -14,48 +18,55 @@ public abstract class DistinctCounter { /** * This constructor cannot be used. */ private DistinctCounter() { state = null; } private DistinctCounter() {mem = null;} /** * Constructs an object backed by a given memory size. * @param stateSize The size of the memory backing, in number of integers. * Constructs an DistinctCounter with a given size of memory. * * @param memBits The number of bits of memory available to the counter. */ public DistinctCounter(int stateSize) { state = new Byte[stateSize]; public DistinctCounter(int memBits) { mem = new FixedBitArray(memBits); } /** * Creates a DistinctCounter object from a given initial state. * @param initialState The output of a call to {@link #currentState()} on some DistinctCounter object. * Sets the memory of this DistinctCounter object to <code>initialMem</code>. * * @param initialMem The memory to set for this object. * It should be in the same format as the output of a call to {@link #currentState()} * for some DistinctCounter object. */ public DistinctCounter(Byte[] initialState) { state = new Byte[initialState.length]; System.arraycopy(initialState, 0, state, 0, initialState.length); public void setMem(FixedBitArray initialMem) { if (mem.len != initialMem.len) throw new IllegalArgumentException( "Trying to set memory with an incompatible argument."); else { // copy initialMem bits to this object mem.bits.clear(); mem.bits.xor(initialMem.bits); } } // ... OPERATIONAL /** * Log a new element that is seen. * Note a new element that is seen. * * @param newElement The element that was seen. */ abstract void saw(String newElement); /** * * @return A guess of the number of distinct elements that were seen. */ abstract Integer numDistinct(); // ... INFORMATIONAL /** * outputs the current state of the DistinctCounter * */ public Byte[] currentState() { return state; } // NESTED CLASSES public static class NotYetImplemented extends RuntimeException { */ final public FixedBitArray currentState() { return mem; } }
src/edu/bu/ec504/hw1p1/FixedBitArray.java 0 → 100644 +114 −0 Original line number Diff line number Diff line package edu.bu.ec504.hw1p1; import java.util.BitSet; /** * Implements aan array of bits whose size cannot be changed. */ public class FixedBitArray { // FIELDS /** * The length, in bits, of this array. */ public final int len; /** * The bits stored in this array. */ final BitSet bits; // METHODS /** * Constructs an object that handles <code>theLen</code> bits. * * @param theLen The number of bits that the object can handle. */ public FixedBitArray(int theLen) { len = theLen; bits = new BitSet(len); } public FixedBitArray(byte[] bytes) { len = bytes.length; bits = BitSet.valueOf(bytes); } /** * @param bitIndex The index at which the array is being queried. * @return The bit at the array index <code>bitIndex</code>. */ public boolean get(int bitIndex) { confirmIndex(bitIndex); return bits.get(bitIndex); } /** * Sets the bit at index <code>bitIndex</code> to true. * * @param bitIndex The index to set true. */ public void set(int bitIndex) { confirmIndex(bitIndex); bits.set(bitIndex); } /** * Clears the bit at index <code>bitIndex</code> to true. * * @param bitIndex The index to set true. */ public void clear(int bitIndex) { confirmIndex(bitIndex); bits.clear(bitIndex); } /** * Flips the parity of the bit at index <code>bitIndex</code> * * @param bitIndex The index of the bit in the array to flip. */ public void flip(int bitIndex) { confirmIndex(bitIndex); bits.flip(bitIndex); } /** * @return A byte array corresponding to memory of this object */ public byte[] toByteArray() { rectifyBits(); return bits.toByteArray(); } /** * @param bytes The contents of the new array. * @return A FixedBitArray whose contents are <code>bytes</code> */ static public FixedBitArray valueOf(byte[] bytes) { return new FixedBitArray(bytes); } @Override public String toString() { return "[" + len + " bits]: " + bits.toString(); } /** * Confirms that <code>bitIndex</code> is within the dynamic range of indices * handled by this array, returning normally if confirmation succeeds. * * @param bitIndex The index to check. * @throws ArrayIndexOutOfBoundsException if <bode>bitIndex</bode> is out of * range for this array. */ private void confirmIndex(int bitIndex) { if (bitIndex < 0 || bitIndex >= len) {throw new ArrayIndexOutOfBoundsException(bitIndex);} } /** * Make sure there are no bits outside the dynamic range of the array. */ private void rectifyBits() { bits.set(len, bits.size(), false); } }
src/edu/bu/ec504/hw1p1/Main.java +16 −10 Original line number Diff line number Diff line Loading @@ -2,31 +2,37 @@ package edu.bu.ec504.hw1p1; import java.math.BigInteger; import java.util.ArrayList; import java.util.Arrays; import java.util.HashSet; import java.util.List; import java.util.Set; public class Main { // constants static final int stateSize = 10; // the number of bytes in the myDistinctCounter object static final int memSize = 10; // the number of bits backing the counter /** * Run {@link myDistinctCounter} through the test strings provided, and report its results. * @param testStrings The strings to run by the {@link myDistinctCounter}. * Run {@link MyDistinctCounter} through the test strings provided, and report its results. * @param testStrings The strings to run by the {@link MyDistinctCounter}. */ static void test(ArrayList<String> testStrings) { // Show the counter my test strings myDistinctCounter tester = new myDistinctCounter(stateSize); MyDistinctCounter tester = new MyDistinctCounter(memSize); Set<String> verifier = new HashSet<>(); for (String test: testStrings) { tester.saw(test); verifier.add(test); } // Record the counter's state Byte[] savedState = tester.currentState(); System.out.println("Counter state is: "+ Arrays.toString(savedState)); FixedBitArray savedState = tester.currentState(); System.out.println("Counter state is: "+ savedState); // Output the prediction myDistinctCounter newFoo = new myDistinctCounter(savedState); System.out.println("# of distinct strings: "+newFoo.numDistinct()); // Output the guess MyDistinctCounter newFoo = new MyDistinctCounter(memSize); newFoo.setMem(savedState); System.out.println("guessed # of distinct strings: "+newFoo.numDistinct()); System.out.println(" actual # of distinct strings: "+verifier.size()); } /** Loading
src/edu/bu/ec504/hw1p1/myDistinctCounter.java→src/edu/bu/ec504/hw1p1/MyDistinctCounter.java +10 −10 Original line number Diff line number Diff line package edu.bu.ec504.hw1p1; public class myDistinctCounter extends DistinctCounter { public class MyDistinctCounter extends DistinctCounter { /** * @inheritDoc */ public myDistinctCounter(int stateSize) { super(stateSize); public MyDistinctCounter(int memBits) { super(memBits); throw new NotYetImplemented(); // replace this with your code! } /** * @inheritDoc */ public myDistinctCounter(Byte[] initialState) { super(initialState); @Override void saw(String newElement) { throw new NotYetImplemented(); // replace this with your code! } Loading @@ -22,15 +22,15 @@ public class myDistinctCounter extends DistinctCounter { * @inheritDoc */ @Override void saw(String newElement) { Integer numDistinct() { throw new NotYetImplemented(); // replace this with your code! } // NESTED CLASSES /** * @inheritDoc * A runtime exception indicating that a method has not yet been implemented. */ @Override Integer numDistinct() { throw new NotYetImplemented(); // replace this with your code! public static class NotYetImplemented extends RuntimeException { } }