I'm trying to create a method in java to validate a dutch postal code.
the dutch postal code consist 6 characters which contain 4 numbers (first 4 chars) and 2 letters (last 2 chars) so for example 1010AB.
I made a boolean to return false if the postcode is not within standard and true if it is.
I'm getting stuck with checking the last 2 letters.
I've created a loop for the first 4 numbers, but I don't know how to go further from here to check the letters aswell.
My java method:
public static boolean checkPostcode(String postCode) {
boolean value = false;
if (postCode.length() == lengthPost) {
for (int i = 0; i < postCode.length(); i++) {
if (i <= 4) {
if (Character.isDigit(postCode.charAt(i)) {
value = true;
else{
if (Character.isLetter(postCode.charAt(i))) {
value = true;
}
}
}
}
}
}
return value;
}
You van ignore the last else, because that is the point where I get stuck....
If someone can help me that would be great!!
Thanks in advance
Solution using regex:
public class Main {
public static void main(String[] args) {
// Tests
System.out.println(checkPostcode("1234AB"));
System.out.println(checkPostcode("5678MN"));
System.out.println(checkPostcode("0123AB"));
System.out.println(checkPostcode("1023AB"));
System.out.println(checkPostcode("1230AB"));
System.out.println(checkPostcode("AB1234"));
System.out.println(checkPostcode("123456"));
System.out.println(checkPostcode("ABCDEF"));
System.out.println(checkPostcode("12345A"));
System.out.println(checkPostcode("A12345"));
System.out.println(checkPostcode("A12345B"));
System.out.println(checkPostcode("1ABCDE6"));
System.out.println(checkPostcode("1ABCD6"));
}
public static boolean checkPostcode(String postCode) {
return postCode.matches("[1-9]{1}[0-9]{3}[a-zA-Z]{2}");
}
}
Output:
true
true
false
true
true
false
false
false
false
false
false
false
false
Non-regex solution:
public static boolean checkPostcode(String postCode) {
if (postCode.length() != lengthPost || postCode.charAt(0) == '0') {
return false;
}
if (postCode.length() == lengthPost) {
for (int i = 0; i < postCode.length(); i++) {
if (i < 4 && Character.isLetter(postCode.charAt(i))) {
return false;
}
if (i > 3 && Character.isDigit(postCode.charAt(i))) {
return false;
}
}
}
return true;
}
If I understand correctly, the first 4 symbols are digits, so the if condition should be
(i < 4)
because otherwise you check the first 5 symbols for a digit
While you could solve this problem with regular expressions, it is also possible to solve it along the lines you have chosen. I would write two helper methods, one to check that all characters within a given subsequence of a String are digits and another to check for letters. Like,
private static boolean allDigits(String s, int start, int end) {
for (int i = start; i < end; i++) {
if (!Character.isDigit(s.charAt(i))) {
return false;
}
}
return true;
}
private static boolean allLetters(String s, int start, int end) {
for (int i = start; i < end; i++) {
if (!Character.isLetter(s.charAt(i))) {
return false;
}
}
return true;
}
Then the checkPostcode can delegate to those two methods. Like,
public static boolean checkPostcode(String postCode) {
if (postCode != null && postCode.length() == 6) {
return allDigits(postCode, 0, 4) && allLetters(postCode, 4, 6);
}
return false;
}
And if you choose to use a regular expression compile it with a Pattern for better performance. Like,
private static Pattern POSTCODEPATTERN = Pattern.compile("\\d{4}[A-Za-z]{2}");
public static boolean checkPostcode(String postCode) {
return postCode != null && POSTCODEPATTERN.matcher(postCode).matches();
}
Related
We define balanced number as number which has the same number of even and odd dividers e.g (2 and 6 are balanced numbers). I tried to do task for polish SPOJ however I always exceed time.
The task is to find the smallest balance number bigger than given on input.
There is example input:
2 (amount of data set)
1
2
and output should be:
2
6
This is my code:
import java.math.BigDecimal;
import java.util.Scanner;
public class Main {
private static final BigDecimal TWO = new BigDecimal("2");
public static void main(String[] args) throws java.lang.Exception {
Scanner in = new Scanner(System.in);
int numberOfAttempts = in.nextInt();
for (int i = 0; i < numberOfAttempts; i++) {
BigDecimal fromNumber = in.nextBigDecimal();
findBalancedNumber(fromNumber);
}
}
private static boolean isEven(BigDecimal number){
if(number.remainder(new BigDecimal("2")).compareTo(BigDecimal.ZERO) != 0){
return false;
}
return true;
}
private static void findBalancedNumber(BigDecimal fromNumber) {
BigDecimal potentialBalancedNumber = fromNumber.add(BigDecimal.ONE);
while (true) {
int evenDivider = 0;
int oddDivider = 1; //to not start from 1 as divisor, it's always odd and divide potentialBalancedNumber so can start checking divisors from 2
if (isEven(potentialBalancedNumber)) {
evenDivider = 1;
} else {
oddDivider++;
}
for (BigDecimal divider = TWO; (divider.compareTo(potentialBalancedNumber.divide(TWO)) == -1 || divider.compareTo(potentialBalancedNumber.divide(TWO)) == 0); divider = divider.add(BigDecimal.ONE)) {
boolean isDivisor = potentialBalancedNumber.remainder(divider).compareTo(BigDecimal.ZERO) == 0;
if(isDivisor){
boolean isEven = divider.remainder(new BigDecimal("2")).compareTo(BigDecimal.ZERO) == 0;
boolean isOdd = divider.remainder(new BigDecimal("2")).compareTo(BigDecimal.ZERO) != 0;
if (isDivisor && isEven) {
evenDivider++;
} else if (isDivisor && isOdd) {
oddDivider++;
}
}
}
if (oddDivider == evenDivider) { //found balanced number
System.out.println(potentialBalancedNumber);
break;
}
potentialBalancedNumber = potentialBalancedNumber.add(BigDecimal.ONE);
}
}
}
It seems to work fine but is too slow. Can you please help to find way to optimize it, am I missing something?
As #MarkDickinson suggested, answer is:
private static void findBalancedNumberOptimized(BigDecimal fromNumber) { //2,6,10,14,18,22,26...
if(fromNumber.compareTo(BigDecimal.ONE) == 0){
System.out.println(2);
}
else {
BigDecimal result = fromNumber.divide(new BigDecimal("4")).setScale(0, RoundingMode.HALF_UP).add(BigDecimal.ONE);
result = (TWO.multiply(result).subtract(BigDecimal.ONE)).multiply(TWO); //2(2n-1)
System.out.println(result);
}
}
and it's finally green, thanks Mark!
I was asked in an interview to write code to check if a given string is a palindrome or can be a palindrome by altering some character without using a library function. Here is my Approach
import java.util.Scanner;
public class Palindrom {
static int temp=0;
static char[] cArr;
static boolean chackPotentialPalindrom(char[] cAr){
cArr=cAr;
if(cArr!=null){
char current=cArr[0];
for(int i=1;i<cArr.length;i++){
if(current==cArr[i]){
cArr=removeElement(i);
chackPotentialPalindrom(cArr);
break;
}
}
if(cAr.length==2){
if(cAr[0]==cAr[1]){
cArr=null;
}}
if(temp==0 && cArr!=null){
temp=1;
cArr=removeFirstElement(cArr);
chackPotentialPalindrom(cArr);
}
}
if(cArr==null){
return true;
}else{
return false;
}
}
static char[] removeFirstElement(char[] cAr){
cArr=cAr;
if(cArr!=null){
if(cArr.length >1){
char[] cArrnew=new char[cArr.length-1];
for(int j=1,k=0;j<cArr.length;j++,k++){
cArrnew[k]=cArr[j];
}
return cArrnew;
} else {
return null;
}
} else {
return null;
}
}
static char[] removeElement(int i){
if(cArr.length>2){
char[] cArrnew=new char[cArr.length-2];
for(int j=1,k=0;j<cArr.length;j++,k++){
if(i!=j){
cArrnew[k]=cArr[j];
}else{
k-=1;
}
}
return cArrnew;}
else{
return null;
}
}
public static void main(String[] args) {
Scanner scn=new Scanner(System.in);
while(true){
temp=0;
String s=scn.next();
char[] arr=s.toCharArray();
System.out.println(chackPotentialPalindrom(arr));
}
}
}
Any tips to optimize this code?I could not write this in an interview as they have given a pen and paper to code.It took 3 hrs for me to write this. Can I be a developer?
Title says "without loop" but you need to check all symbol pairs, so using recursion, as you have tried, looks reasonable. But you don't check and use results of recursive calls.
Pseudocode might look like (note we don't need to change source data or extract substring):
Edit to provide possibility to alter one char
boolean checkPotentialPalindrom(char[] cAr, start, end, altcnt){
if (end <= start)
return true
if (cAr[start] != cAr[end])
altcnt = altcnt + 1
if (altcnt > 1)
return false
return checkPotentialPalindrom(cAr, start + 1, end - 1, altcnt)
}
and make the first call with arguments 0, len(cAr-1), 0
Answering to your first question..You have to use recursion to solve this problem. Here is my approach.
public boolean isPalindrom(char[] str, int start, int end) {
if (end <= start)
return true;
if (str[start] != str[end] || arraySize(str) <= 1)
return false;
return isPalindrom(str, start + 1, end - 1);
}
public int arraySize(char[] str) {
int count = 0;
for (char i : str) {
count++;
}
return count;
}
You have tried to implement this algorithm using loops and you can simplify it like this
public boolean isPalindroms(char[] str) {
int diffCount = 0;
int left = 0;
int right = arraySize(str) - 1;
while (right > left) {
if (str[right--] != str[left++]) {
diffCount++;
}
}
return (diffCount < 2);
}
public int arraySize(char[] str) {
int count = 0;
for (char i : str) {
count++;
}
return count;
}
The answer for the second question that you have ask is definitely you can be a good developer. Computer programming is a Craft. Not Some Kind of Rocket Science. You have to master it by crafting it.
using recursive function
calling with left=0 and right = arr.length-1
public static boolean isPalindrom(char[] arr, int left, int right){
if(arr[left++] != arr[right--])
return false;
if(left < right)
isPalindromss(arr, left++, right--);
return true;
}
if you have to use while loop, you can simplify it like following
public boolean isPalindrom(char[] arr){
int left=0;
int right = arr.length-1;
while(left < right){
if(arr[left++] == arr[right--])
continue;
return false;
}
return true;
}
Using StringBuilder, We can do it
public static boolean isPalindrom(String str, int len){
StringBuilder sb= new StringBuilder(str);
if((len > 1) & !(sb.substring(0,len/2 + 1).equals(sb.reverse().substring(0,len/2 + 1))))
return false;
return true;
}
function palin(input, leftIdx = 0, rightIdx = input.length - 1) {
if (leftIdx >= rightIdx) return true;
if (input[leftIdx] != input[rightIdx]) return false;
return palin(input, leftIdx + 1, rightIdx - 1);
}
const testCases = {
air: false,
airia: true,
caria: false,
a: true,
bb: true,
bcdb: false,
zzaaaaz: false,
};
Object.keys(testCases).forEach(test =>
console.log("Test: ", test, " is palindrome: ", palin(test), testCases[test])
);
I have a helper method that I am calling from another method in the same class. When I test it from main, it works fine. But as soon as I use it in the other class, it doesn't work at all. I cannot figure out what is wrong.
This is the helper method:
private boolean checkStack(Stack<String> stack,String check) {
System.out.println(stack);
System.out.println(check);
Stack<String> jump = new Stack<String>();
int count = 0;
String temp = "";
while (!stack.empty()) {
temp = stack.pop();
if (check == temp) {
count++;
}
jump.push(temp);
}
while (!jump.empty()) {
temp = jump.pop();
stack.push(temp);
}
System.out.println(count);
if (count != 0) {
return true;
} else {
return false;
}
}
I will test it from main like so:
pathSoFar.push("00");
pathSoFar.push("01");
pathSoFar.push("20");
pathSoFar.push("23");
System.out.println(pathSoFar);
String checkfor = "20";
System.out.println(test01.checkStack(pathSoFar,checkfor));
But it wont work when I call it from another method:
for (String n : possibleSpots) {
System.out.println();
String check = n;
if (!checkStack(pathSoFar, n)) {
pathSoFar.push(n);
String x = ""+n.charAt(0);
String y = ""+n.charAt(1);
int nextRow = Integer.parseInt(x);
int nextCol = Integer.parseInt(y);
System.out.println(nextRow + "" + nextCol + " = next move.");
if (findPath(wordToFind, pathSoFar, nextRow, nextCol)) {
return true;
}
} else{}
}
This is the method header if that helps:
private boolean findPath(String wordToFind, Stack<String> pathSoFar, int row, int col) {
possibleSpots can contain either String literals or String objects.
The problem lies in the following line
if (check == temp)
Change it to
if (check.equals(temp))
String matching is done with == which will work only for String literals.
That is the reason why it worked for you in one case and it does not work in another case.
To know the difference check the below link:
What is the difference between == vs equals() in Java?
in this method i have tried to set row =0 , row =1 row =2 row =3 row =4 and the result is always false. i think its something considering the initilization of the variable valid but if i do not initialize the compiler comes up with error
public static boolean isValidMove(int row,int col){
boolean valid=false;
if(row>=0&&row<3&&col>=0&&col<3){
if (takenSquare[row][col]==false) {
valid= true;
}
}
Seems like your condition is never evaluated at all
public static boolean isValidMove( int nRow,int nCol ) {
boolean blValid = false;
if( ( nRow >= 0 && nRow < 3 ) && ( nCol >= 0 && nCol < 3 ) ) {
if ( arTakenSquare[ nRow ][ nCol ] == false ) {
blValid = true;
}
}
return blValid;
}
May be this would help.
Your code is valid (for values from 0 to 2). Of course you need a return statment. The only thing that can be wrong is takenSquare[row][col]==false. Is that a array of boolean values?
This is not an answer, but an extension to my comment suggesting an SSCCE. I have taken the code from the question, and wrapped it in a simple test program. To complete the isValidMove method I added a return of valid and a }.
It prints row=0, col=0: true. This confirms the bug is not in the code quoted in the question.
The next step is for the OP to either modify this until it reproduces the problem, or simplify the rest of the OP's program until it is about this long. Either way, the objective is a short, simple program that compiles, runs, and demonstrates the problem. Often, the attempt write such a thing will bring out the bug. If it does not, posting the SSCCE will certainly get a useful answer.
public class Test
{
private static boolean[][] takenSquare = new boolean[3][3];
public static void main(String[] args) {
System.out.println("row=0, col=0: "+isValidMove(0,0));
}
public static boolean isValidMove(int row, int col) {
boolean valid = false;
if (row >= 0 && row < 3 && col >= 0 && col < 3) {
if (takenSquare[row][col] == false) {
valid = true;
}
}
return valid;
}
}
================================================================
Here's a revised version of my test program that demonstrates instrumenting isValidMove so that it is clear what arguments it was passed, what it is returning, and why it is returning false any time it does so.
public class Test
{
private static boolean[][] takenSquare = new boolean[3][3];
public static void main(String[] args) {
takenSquare[1][1] = true;
test(0,0);
test(0,-1);
test(1,1);
}
private static void test(int row, int col){
System.out.println("Test result: row="+row+", col="+col+", valid="+isValidMove(row, col));
}
public static boolean isValidMove(int row, int col) {
boolean valid = false;
if (row >= 0 && row < 3 && col >= 0 && col < 3) {
if (takenSquare[row][col] == false) {
valid = true;
} else {
System.out.println("isValidMove square already taken for row="+row+", col="+col);
}
} else {
System.out.println("isValidMove out of range argument row="+row+" col="+col);
}
System.out.println("Returning "+valid+" from isValidMove("+row+","+col+")");
return valid;
}
}
This question already has answers here:
Closed 10 years ago.
Possible Duplicate:
Hide input on command line
I'm making a password security checker program and my question is odd in that my program runs just fine. What I'm wondering is whether there is any way of making text entered to the console appear as it would in a password field. i.e the word entered will appear as "****" BEFORE the user presses the return key.
I am aware that JFrame has a JPasswordField method but I don't think that helps me when in just using Scanner.
Here is my code:
import java.util.Scanner;
public class SecurityCheckerMain {
static String enteredPassword;
public static void main(String[] args) {
Scanner input = new Scanner(System.in);
System.out.println("Please enter your password: ");
enteredPassword = input.nextLine();
Checker tc = new Checker(enteredPassword);
tc.checkSecurity();
}
}
public class Checker {
//number of chars : the Higher the Better("password must be greater than 8 chars"){done}
//combination of uppercase and lowercase{done}
//contains numbers{done}
//non repeated characters (every char is different ascii char){done}
//is not a consecutive password ie 123456789 or 987654321{done}
//is not blank ("[space]"){done}
int pLength;
final int MAX_STRENGTH = 10;
int pStrength = 0;
String pass;
public Checker(String pwd){
pass = pwd;
pLength = pwd.length();
}
public void checkSecurity(){
if(pass.isEmpty()){
System.out.println("Password Field is Empty! Password is Very Insecure.");
}
if(pLength >= 8){
pStrength++;
if(pLength >= 12){
pStrength++;
if(pLength >= 16){
pStrength++;
}
}
}
if(hasUpperCase(pass) && hasLowerCase(pass)){
pStrength+=2;
}
if(containsNumbers(pass)){
pStrength+=2;
}
if(hasNoRepeats(pass)){
pStrength+=2;
}
if(!containsConsecutiveNums(pass)){
pStrength++;
}
System.out.println("Your password strength is rated at " + pStrength +"/" + MAX_STRENGTH);
}
//Component Methods
public boolean hasUpperCase(String str){
for(int i = 0; i<pLength; i++){
if(Character.isUpperCase(str.charAt(i))){
return true;
}
}
return false;
}
public boolean hasLowerCase(String str){
for(int i = 0; i<pLength; i++){
if(Character.isUpperCase(str.charAt(i))){
return true;
}
}
return false;
}
public boolean containsNumbers(String str){
for(int i = 0; i<pLength; i++){
if(Character.isDigit(str.charAt(i))){
return true;
}
}
return false;
}
public boolean hasNoRepeats(String str){
for(int i = 0; i<pLength; i++)
if(containsChar(str, str.charAt(i))){
return false;
}
return true;
}
public boolean containsChar(String s, char search) {
if (s.length() == 0)
return false;
else
return s.charAt(0) == search || containsChar(s.substring(1), search);
}
public boolean containsConsecutiveNums(String str){
for(int i = 0; i<pLength; i++){
if(Character.isDigit(str.charAt(i))){
if(str.charAt(i)-1 == str.charAt(i-1) || str.charAt(i)+1 == str.charAt(i+1)){
return true;
}
}
}
return false;
}
}
You can use Console.readPassword instead.
readPassword(String fmt, Object... args)
Provides a formatted prompt, then reads a password or passphrase from
the console with echoing disabled
public class SecurityCheckerMain {
static String enteredPassword;
public static void main(String[] args) {
Console console = System.console();
enteredPassword =
new String(console.readPassword("Please enter your password: "));
Checker tc = new Checker(enteredPassword);
tc.checkSecurity();
}