I did a lot of searching on this subject, but I couldn't find anything usable for my problem: I'm making a simple memory game in Java based on an integer array. I want the array to contain only duplicate entries and no unique ones. Unfortunately most of the questions here are dealing with avoiding or removing duplicate entries, but what about enforcing them?
My code so far looks like this.
public Field[] getField(){
Random r = new Random();
int pool = 16;
ArrayList<Integer> used = new ArrayList<Integer>();
int rand = r.nextInt(pool);
System.out.println("First random: " + rand);
for(int i = 0; i < fields.length; i++){
System.out.println("ITERATION " + i + " STARTED");
while(used.contains(rand)){
System.out.println(rand + " is used, recalculating...");
rand = r.nextInt(pool);
System.out.println("New random is " + rand);
}
fields[i] = new Field(rand);
System.out.println(rand + " added in Field " + i);
int tmp = r.nextInt(fields.length - 1);
System.out.println("First tmp calculated: " + tmp);
while(fields[tmp] != null && i <= fields.length / 2){
tmp = r.nextInt(fields.length - 1);
System.out.println("Field " + tmp + " is used, looking for another...");
}
fields[tmp] = new Field(rand);
System.out.println(rand + " added in temp Field " + tmp);
used.add(rand);
System.out.println("ITERATION " + i + " ENDED");
System.out.println();
}
return fields;
}
fields[] is an array of the type Field (basically has just one member (int id).
If I'm understanding what you're after correctly, I think you're probably making this a lot harder than it has to be.
It is much easier to iterate over your fields array in order and add two Fields of the same value each iteration, then shuffle the array. Something like the following code:
{
...
for (int i = 0; i < fields.length; i += 2)
fields[i] = fields[i + 1] = new Field(r.nextInt(pool));
shuffleFields(fields);
return fields;
}
You can take your pick of shuffling algorithms. The Fisher-Yates shuffle is popular. E.g.:
void shuffleFields (Field[] fields)
{
Random r = new Random();
for (int i = fields.length - 1; i >= 1; --i)
{
int j = r.nextInt(i + 1);
Field t = fields[i];
fields[i] = fields[j];
fields[j] = temp;
}
}
Related
I made a code that gives me every possible 4 character combination of a String.
Now I need to make a program that chooses 1 random combination as a Password and then goes over every possible combination till it finds the chosen one and then tells me how many guesses it took to find the right one. This is what I have so far:
String alphabet = "ABCabc012!";
char pw[] = alphabet.toCharArray();
for (int i = 0; i < pw.length ; i++) {
for (int j = 0; j < pw.length ; j++) {
for (int k = 0; k < pw.length ; k++) {
for (int l = 0; l < pw.length ; l++) {
System.out.println(pw[i] + " " + pw[j] + " " + pw[k] + " " + pw[l]);
}
}
}
}
I tried to store the pw[] in an array but I dont know exactly how to do it.
Do you really need to store the values in a list beforehand?
Do you need to generate each value exactly once, or it does not matter?
If you can just generate random passwords of size 4 N times, you could try something like this:
public class RandomPass {
static Random random = new Random();
public static void main(String[] args) {
String alphabet = "ABCabc012!";
String password = generatePassword(4, alphabet);
System.out.println("PW is: " + password);
int counter = 0;
while (!generatePassword(4, alphabet).equals(password)) {
counter++;
}
System.out.println("It took: " + counter + " times.");
}
private static String generatePassword(int size, String alphabet) {
StringBuilder pw = new StringBuilder();
for (int i = 0; i < size; i++) {
pw.append(alphabet.charAt(random.nextInt(0, alphabet.length())));
}
return pw.toString();
}
}
If you really need to store them, so do it inside an ArrayList, instead of printing them as you are doing in your code.
After that, you can just traverse the ArrayList and search for your password in there.
You're actually pretty close!
Here's how to build the combinations, add them to the ArrayList, output them, pick a random password from the list, then randomly generate passwords until you get a match:
public static void main(String[] args) {
String alphabet = "ABCabc012!";
char pw[] = alphabet.toCharArray();
// generate the combinations
ArrayList<String> combos = new ArrayList<>();
for (int i = 0; i < pw.length ; i++) {
for (int j = 0; j < pw.length ; j++) {
for (int k = 0; k < pw.length ; k++) {
for (int l = 0; l < pw.length ; l++) {
String pwCombo = "" + pw[i] + pw[j] + pw[k] + pw[l];
combos.add(pwCombo);
}
}
}
}
// output the combinations
for(String password : combos) {
System.out.println(password);
}
// pick a random passwrod
Random r = new Random();
int index = r.nextInt(combos.size());
String pwToGuess = combos.get(index);
System.out.println("Password to guess: " + pwToGuess);
// randomly generate a password until it matches
int tries = 0;
String pwGuess = "";
do {
tries++;
pwGuess = "" + pw[r.nextInt(pw.length)] + pw[r.nextInt(pw.length)] + pw[r.nextInt(pw.length)] + pw[r.nextInt(pw.length)];
} while (!pwGuess.equals(pwToGuess));
System.out.println("It took " + tries + " tries to guess the password!");
}
I have been building an app that simulates the way a printer works. While designing the app, I have created the method below that splits a String content depending on the number of pages required. All the function seems to process the data correctly but I don't know why the method keeps doubling the content of an array it's supposed to return. Here's the method.
public ArrayList<String> splitContentIntoPages(){
int startPosition = 0;
int endIndexCalc = 0;
for(int i=0; i<getPages(); i++){
if((getContent().length() - endIndexCalc) >= getSize().getCapacity()){
System.out.println("Start " + startPosition);
endIndexCalc = startPosition + (getSize().getCapacity());
this.pagesContent.add(getContent().substring(startPosition, endIndexCalc));
startPosition += getSize().getCapacity();
System.out.println("End " + endIndexCalc);
}else{
this.pagesContent.add(getContent().substring(startPosition));
}
}
System.out.println("Size of the array " + this.pagesContent.size() + " getPages() " + getPages() + "");
for(int i=0; i<this.pagesContent.size(); i++){
System.out.println("The content :" + this.pagesContent.get(i));
}
return this.pagesContent;
}
I need some fresher eye on the issue. I have spent too much time on that trying to understand what's wrong. Thanks a lot guys!
Here's the version without debugs
public ArrayList<String> splitContentIntoPages(){
int startPosition = 0;
int endIndexCalc = 0;
for(int i=0; i<getPages(); i++){
if((getContent().length() - endIndexCalc) >= getSize().getCapacity()){
endIndexCalc = startPosition + (getSize().getCapacity());
this.pagesContent.add(getContent().substring(startPosition, endIndexCalc));
startPosition += getSize().getCapacity();
}else{
this.pagesContent.add(getContent().substring(startPosition));
}
}
return this.pagesContent;
}
this is the test entry extraxt. Basically the method aboe is processing the string of chars
that's the outcome. Basically, the string is supposed to be split into the number of pages - in this case 2. However, the array that is holding the split element of the strings holds 4 pieces of strings instead of two. It's all doubled. And I have no idea why
Either clear this.pagesContent at the beginning of splitContentIntoPages() or create new ArrayList<String> newA = new ArrayList<String>() at the beginning, add everythig to this new arrayList and at the end of splitContentIntoPages() do this.pagesContent = newA
I have two lists which contains some values,I have to make String from them so that i will take the 1st value of first list and 1 st value of 2 nd list and also 2nd value of first list and 2 nd value of 2nd list and so on..Lets says those two lists contains the interview timings.So i am giving my code here
List<String> interviewTimingToFrom1 = Arrays.asList(interviewTime1.split(","));
for(String a :interviewTimingToFrom1){
System.out.println("Timing 1:"+a);
}
List<String> interviewTimingToFrom2 = Arrays.asList(interviewTime2.split(","));
for(String a :interviewTimingToFrom2){
}
The values contain in the 1 st and 2nd list are
Timing 1:12:00am
Timing 1:2:00am
Timing 2:1:00am
Timing 2:3:00am
So now i need to make a string like from 12.00am to 1.00 am ,from 2.00 am to 3.00am how i can do that .Please help
int maxSize = Math.max(interviewTimingToFrom1.size(),interviewTimingToFrom2.size());
StringBuilder result = new StringBuilder();
for (int i=0; i<maxSize; i++)
{
if (i < interviewTimingToFrom1.size())
result.append(interviewTimingToFrom1.get(i));
if (i < interviewTimingToFrom2.size())
result.append(interviewTimingToFrom2.get(i));
}
System.out.println(result.toString());
Try this;
List<String> interviewTimingToFrom1 = Arrays.asList(interviewTime1.split(","));
List<String> interviewTimingToFrom2 = Arrays.asList(interviewTime2.split(","));
if (interviewTimingToFrom1.size() == interviewTimingToFrom2.size()) {
int noOfSlots = interviewTimingToFrom1.size();
for (int i = 0; i < noOfSlots; i++) {
System.out.println("from " + interviewTimingToFrom1.get(i)
+ " to " + interviewTimingToFrom1.get(i));
}
} else {
System.out.println("No match");
int noOfSlots = (interviewTimingToFrom1.size() > interviewTimingToFrom2
.size() ? interviewTimingToFrom2.size()
: interviewTimingToFrom1.size());
for (int i = 0; i < noOfSlots; i++) {
System.out.println("from " + interviewTimingToFrom1.get(i)
+ " to " + interviewTimingToFrom2.get(i));
}
}
I need to implement a delete method WITHOUT USING AN ARRAY LIST. I need to use a set of loops to do it. Here is my delete method and add method as well as any other important variables used. Any advice on what is wrong with my code would be great.
EDITED: Changed the comparing of references to values. Seems to work repeatedly.
final int MAX_DEVICES = 5;
// Array of devices
private Device list[] = new Device[MAX_DEVICES];
// Number of Devices currently in the list
// "Valid" Devices are stored in cells 0 - (numDevices - 1)
private int numDevices = 0;
Scanner stdin; // read from stdin
private void Add()
{
String thisName;
int numThisRead;
float thisInitVal;
thisName = stdin.next();
numThisRead = stdin.nextInt();
thisInitVal = stdin.nextFloat();
if(numDevices > MAX_DEVICES)
System.out.println("The List was full. " + thisName +
" was not added to the list.");
else
{
Device myDevice = new Device(thisName, numThisRead, thisInitVal);
list[numDevices] = myDevice;
numDevices ++;
System.out.println(thisName + " device has been added to the list.");
}
}
private void Delete() //ASK QUESTION
{
String thisDelete;
thisDelete = stdin.next();
for(int i = 0; i < MAX_DEVICES; ++i)
{
if(list[i].getName().equals(thisDelete)) //if you find the name
{
System.out.println(list[i].getName() + " was deleted from the "
+ "list.");
for(int j = i; j < numDevices - 1; j++)
list[j] = list[j + 1];
numDevices--;
return;
}
}
System.out.println(thisDelete + " not deleted. It is not in the list.");
}
If you need to avoid using data type List, you can place the objects in the array. Then you can declare an array one element smaller than the current array and copy all the elements, except for the one you want deleted, over into the new array. Then return the new array.
I'm fairly new to java and have come across a problem. My task is to create a class which contains a method write(Object obj) that writes the type of the object as well as the name and type of all attributes into a file. Recursion is involved since the object may have objects/arrays of objects as attributes.
Here is the code:
public void write(Object obj) throws Exception {
if(obj == null)
{
out.close();
return;
}
Class c = obj.getClass();
Class d;
Field fields_c[] = c.getDeclaredFields();
System.out.println("class_name:" + c.getName());
int i, j;
String tab = new String("");
for(i = 0; i < indent_level; i++)
{
tab = tab + "\t";
}
out.write(tab + "class_name:" + c.getName() + "\n");
for(i = 0; i < fields_c.length; i++) {
System.out.println("field name: " + fields_c[i].getName() + " ");
c = fields_c[i].getType();
fields_c[i].setAccessible(true);
if(c.isPrimitive()) {
out.write("\t" + tab + "field_name:" + c.toString() + "\n");
}
else if(c.isArray()) {
System.out.println("field of type array with elements of type:" + c.getComponentType());
for(j = 0; j < Array.getLength(c); j++)
{
d = Array.get(c, j).getClass();
indent_level = indent_level + 1;
this.write(d);
indent_level = indent_level - 1;
}
}
else
{
System.out.println("field is not primitive of type:" + c.getName());
Object foo = fields_c[i].get(obj);
indent_level = indent_level + 1;
this.write(foo);
indent_level = indent_level - 1;
}
}
}
An exception arises if I call the method and give an Object that has an array attribute; all attributes until the array are written properly to the output file.
The exception is "java.lang.IllegalArgumentException: Argument is not an array".
In d = Array.get(c, j).getClass(); c is of type java.lang.Class, but an array is expected.
You should change it to d = Array.get(fields_c[i].get(obj), j) and use c#getComponentType for get the type of the array.
This may not be what you're after, but if this is to do with serialisation then I recommend "Simple";
http://simple.sourceforge.net/
It makes Java <=> XML serialisation unbelievably easy.
Why you're passing Class of elements instead of elements:
Object[] array = fields_c[i].get(obj);
for(j = 0; j < Array.getLength(array); j++)
{
Object foo = Array.get(array, j); // not .getClass()
indent_level = indent_level + 1;
this.write(foo);
indent_level = indent_level - 1;
}