I'm having a few issues with my zip code validator which reads a text file with UK postcodes then returns true or false after validation.
Below is the section of code I'm having issues with particularly (ZipCodeValidator) which is public and should be declared in a file called ZipCodeValidator.java. And then (Zip) which cannot find symbol.
public class ZipCodeValidator {
private static String regex = "^[A-Z]{1,2}[0-9R][0-9A-Z]? [0-9][ABD-HJLNP-UW-Z]{2}$";
private static Pattern pattern = Pattern.compile(regex);
public boolean isValid(String zipCode) {
Matcher matcher = pattern.matcher(zip);
return matcher.matches();
}
}
And below here is the entire program for reference. Any help is appreciated.
package postcodesort;
import java.util.*;
import java.util.Random;
import java.util.Queue;
import java.util.TreeSet;
import java.io.File;
import java.io.BufferedReader;
import java.io.FileNotFoundException;
import java.io.FileReader;
import java.io.IOException;
import java.util.LinkedList;
import java.util.StringTokenizer;
import java.util.zip.ZipFile;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
public class PostCodeSort
{
Queue<String> postcodeStack = new LinkedList<String>();
public static void main(String[] args) throws IOException
{
FileReader fileReader = null;
ZipCodeValidator zipCodeValidator = new ZipCodeValidator();
// Create the FileReader object
try {
fileReader = new FileReader("postcodes1.txt");
BufferedReader br = new BufferedReader(fileReader);
String str;
while((str = br.readLine()) != null)
{
if(zipCodeValidator.isValid(str)){
System.out.println(str + " is valid");
}
else{
System.out.println(str + " is not valid");
}
}
}
catch (IOException ex)
{
// handle exception;
}
finally
{
fileReader.close();
}
}
}
public class ZipCodeValidator {
private static String regex = "^[A-Z]{1,2}[0-9R][0-9A-Z]? [0-9][ABD-HJLNP-UW-Z]{2}$";
private static Pattern pattern = Pattern.compile(regex);
public boolean isValid(String zipCode) {
Matcher matcher = pattern.matcher(zip);
return matcher.matches();
}
}
Possibly a copy+paste issue, but Matcher matcher = pattern.matcher(zip); doesn't match the method parameter zipCode. Do you have zip defined somewhere else, and possibly validating against that?
It's when I added the read file code thats when the problems arose like the ones I specified above
Make sure you clean up the String before you pass it in. To remove any leading or trailing whitespace characters use
if(zipCodeValidator.isValid(str.strip())){
lastly, your regex only matches upper case. Make sure you allow all cases by using
str.strip().toUpperCase()
or changing your Regex:
private static Pattern pattern = Pattern.compile(regex, Pattern.CASE_INSENSITIVE);
Related
The purpose of this code is to count the instances of letters that occur in sequence, using HashMaps, and Streams.
I've run into the problem of my System.out.print(results) is printing [is=3, imple=2, it=1] to the console, but my junit is saying "expected <[is=3 imple =2 it=1]> but was <[]>.
The code prints out [is=3, imple=2, it=1] but it doesn't seem to actually be updating this out into memory. Any tips or advice on what I should do?
Thank you so much!
import java.util.HashMap;
import java.util.LinkedList;
import java.util.Map;
import java.util.Map.Entry;
import java.util.Scanner;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
import java.io.ByteArrayOutputStream;
import java.io.PrintStream;
import java.util.List;
import java.util.ArrayList;
import java.util.Collections;
public class WordCount {
protected Map<String, Integer> counts;
static Scanner in= new Scanner(System.in);
public WordCount(){
counts = new HashMap<String,Integer>();
}
public Map getCounts(){
return counts;
}
public int parse(Scanner in, Pattern pattern){
int counter=0;
while (in.hasNext()) {
// get the next token
String token = in.next();
// match the pattern within the token
Matcher matcher = pattern.matcher(token);
// process each match found in token (could be more than one)
while (matcher.find()) {
// get the String that matched the pattern
String s = matcher.group().trim();
// now do something with s
counter=counts.containsKey(s) ? counts.get(s):0;
counts.put(s,counter+1);
}
}
return counter;
}
public void report(PrintStream printstream){
List<Map.Entry<String, Integer>> results = new ArrayList<Map.Entry<String, Integer>>();
for(Map.Entry<String, Integer> entry: counts.entrySet()){
results.add(entry);
Collections.sort(results,Collections.reverseOrder(Map.Entry.comparingByValue()));
results.toString();
}
System.out.println(results); // The main problem is this outputs [is=3,
imple=2, it=1] but the junit doesn't pass.
}
}
//Test Cases
import java.io.ByteArrayOutputStream;
import java.io.PrintStream;
import java.util.Scanner;
import java.util.regex.Pattern;
import junit.framework.TestCase;
public class TestWordCount extends TestCase {
public void test_WordCount_parse() {
WordCount wc = new WordCount();
Scanner in = new Scanner("this is a simple test, but it is not simple to pass");
Pattern pattern = Pattern.compile("[i][a-z]+");
wc.parse(in, pattern);
assertEquals((Integer)3, wc.getCounts().get("is"));
assertEquals((Integer)2, wc.getCounts().get("imple"));
assertEquals((Integer)1, wc.getCounts().get("it"));
}
public void test_WordCount_report() {
WordCount wc = new WordCount();
Scanner in = new Scanner("this is a simple test, but it is not simple to pass");
Pattern pattern = Pattern.compile("[i][a-z]+");
wc.parse(in, pattern);
ByteArrayOutputStream output = new ByteArrayOutputStream();
wc.report(new PrintStream(output));
String out = output.toString();
String ls = System.lineSeparator();
assertEquals("is=3_imple=2_it=1_".replace("_", ls), out);
}
`public void report(PrintStream printstream)`
In this method you do not print anything to printstream. Try adding
printstream.print(results);
to this method.
Note that, although System.out is a PrintStream itself, it's a different stream that is bound to the console.
I need help. I'm beginning programmer, I try to make program with regular expression.
I try to find every life word in my file. I have code like this:
import java.io.BufferedReader;
import java.io.FileReader;
import java.io.IOException;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
public class myClass {
public int howManyWord () {
int count = 0;
try {
BufferedReader br = new BufferedReader(new FileReader("C:/myFile.txt"));
String line = "";
while ((line = br.readLine()) != null) {
Matcher m = Pattern.compile("life").matcher(line);
while (m.find()) {
System.out.println("found");
count++;
}
}
} catch (IOException e) {
e.printStackTrace();
}
return count;
}
}
That works. I try to change this because when I'm searching my word and when compilator find something like this "lifelife" count is 2.
What should I change?
Sorry for my English but help me, please.
Use Pattern p = Pattern.compile("\\blife\\b"); and set the pattern once before the while loop.
import java.io.BufferedReader;
import java.io.FileReader;
import java.io.IOException;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
public class myClass {
public int howManyWord () {
int count = 0;
try {
BufferedReader br = new BufferedReader(new FileReader("C:/myFile.txt"));
String line = "";
Pattern p = Pattern.compile("\\blife\\b"); // compile pattern only once
while ((line = br.readLine()) != null) {
Matcher m = p.matcher(line);
while (m.find()) {
System.out.println("found");
count++;
}
}
} catch (IOException e) {
e.printStackTrace();
}
return count;
}
}
"(?<=^|\\W)life(?=$|\\W)" will find words "life" but not "lifelife" or "xlife".
I've written two separate pieces of code. Now I want to merge both pieces of code. Now one part opens a text file and displays the contents of the text file and the second piece of code validates manually entered postcodes. Now I want to read a text file and then automatically validate postcodes within the text file. Not sure how I can merge them. Any questions please ask as I'm stuck.
package postcodesort;
import java.util.*;
import java.util.Random;
import java.util.Queue;
import java.util.TreeSet;
import java.io.File;
import java.io.BufferedReader;
import java.io.FileNotFoundException;
import java.io.FileReader;
import java.io.IOException;
import java.util.LinkedList;
import java.util.StringTokenizer;
public class PostCodeSort
{
Queue<String> postcodeStack = new LinkedList<String>();
public static void main(String[] args) throws IOException
{
FileReader fileReader = null;
// Create the FileReader object
try {
fileReader = new FileReader("postcodes1.txt");
BufferedReader br = new BufferedReader(fileReader);
String str;
while((str = br.readLine()) != null)
{
System.out.println(str + "");
}
}
catch (IOException ex)
{
// handle exception;
}
finally
{
fileReader.close();
}
// Close the input
}
}
Second part that manually validates postcodes:
List<String> zips = new ArrayList<String>();
//Valid ZIP codes
zips.add("SW1W 0NY");
zips.add("PO16 7GZ");
zips.add("GU16 7HF");
zips.add("L1 8JQ");
//Invalid ZIP codes
zips.add("Z1A 0B1");
zips.add("A1A 0B11");
String regex = "^[A-Z]{1,2}[0-9R][0-9A-Z]? [0-9][ABD-HJLNP-UW-Z]{2}$";
Pattern pattern = Pattern.compile(regex);
for (String zip : zips)
{
Matcher matcher = pattern.matcher(zip);
System.out.println(matcher.matches());
}
You should create a class called something like ZipCodeValidator that contains the functionality of your second snippet. It will look something like this
public class ZipCodeValidator {
private static String regex = "^[A-Z]{1,2}[0-9R][0-9A-Z]? [0-9][ABD-HJLNP-UW-Z]{2}$";
private static Pattern pattern = Pattern.compile(regex);
public boolean isValid(String zipCode) {
Matcher matcher = pattern.matcher(zip);
return matcher.matches();
}
}
Then you can create an instance of this class
ZipCodeValidator zipCodeValidator = new ZipCodeValidator();
and then use it in your main method
boolean valid = zipCodeValidator.isValid(zipCode);
Merging your question and the answer by #hiflyer I posted this answer, this makes an assumption that the file postcodes1.txt has all the zip codes in separate lines.
package postcodesort;
import java.util.*;
import java.util.Random;
import java.util.Queue;
import java.util.TreeSet;
import java.io.File;
import java.io.BufferedReader;
import java.io.FileNotFoundException;
import java.io.FileReader;
import java.io.IOException;
import java.util.LinkedList;
import java.util.StringTokenizer;
public class PostCodeSort
{
Queue<String> postcodeStack = new LinkedList<String>();
public static void main(String[] args) throws IOException
{
FileReader fileReader = null;
ZipCodeValidator zipCodeValidator = new ZipCodeValidator();
// Create the FileReader object
try {
fileReader = new FileReader("postcodes1.txt");
BufferedReader br = new BufferedReader(fileReader);
String str;
while((str = br.readLine()) != null)
{
if(zipCodeValidator.isValid(str)){
System.out.println(str + " is valid");
}
else{
System.out.println(str + " is not valid");
}
}
}
catch (IOException ex)
{
// handle exception;
}
finally
{
fileReader.close();
}
}
}
public class ZipCodeValidator {
private static String regex = "^[A-Z]{1,2}[0-9R][0-9A-Z]? [0-9][ABD-HJLNP-UW-Z]{2}$";
private static Pattern pattern = Pattern.compile(regex);
public boolean isValid(String zipCode) {
Matcher matcher = pattern.matcher(zip);
return matcher.matches();
}
}
I’ve a problem finding the proper regex to read a ppm file dimensions. I don’t know if it’s because my regex is wrong or if I misuse the Pattern.compile method, but I get a java.util.NoSuchElementException. Below my regex and the code along to it. It reads the whole file since my regex always return null.
Thanks.
package projet;
import java.awt.Color;
import java.io.File;
import java.io.FileNotFoundException;
import java.io.FileReader;
import java.util.Scanner;
import java.util.logging.Level;
import java.util.logging.Logger;
import java.util.regex.Pattern;
public class Ppm extends File{
private Dimensions d;
private Color[][] p;
public Ppm(String pathname) {
super(pathname);
}
public void read(){
try {
Scanner s=new Scanner(new FileReader(this.getPath()));
while(s.findInLine(Pattern.compile("/^\\d* \\d*\\s$/")) == null && s.hasNext()){
System.out.println(s.nextLine());
}
s.close();
} catch (FileNotFoundException ex) {
Logger.getLogger(Ppm.class.getName()).log(Level.SEVERE, null, ex);
System.out.println("Check filepath.");
}
}
}
Here's my sample file : https://www.dropbox.com/s/z35dvi90zdfkws0/carte1.ppm?dl=0
EDIT :
I tried with a matcher, but it still doesn't work, following the corrected regex. Here's my code, it never matches the pattern...
public class Ppm extends File{
private Dimensions d;
private Color[][] p;
public Ppm(String pathname) {
super(pathname);
d=new Dimensions(0, 0);
}
public void read(){
try {
Scanner s=new Scanner(new FileReader(this.getPath()));
Pattern p=Pattern.compile("^\\d+ \\d+\\s$");
Matcher m;
while(s.hasNext()){
m=p.matcher(s.nextLine());
if(m.matches()){
System.out.println("Found");
}
}
//System.out.println("W : "+d.getWidth()+" H: "+d.getHeight());
} catch (FileNotFoundException ex) {
Logger.getLogger(Ppm.class.getName()).log(Level.SEVERE, null, ex);
System.out.println("Check filepath.");
}
}
}
Your regex can never match.
Pattern.compile("/^\\d* \\d*\\s$/")
asks for a text has a slash before the beginning of the string and after the end of the string. Unlike PHP, Java doesn't use regex delimiters. Try
Pattern.compile("^\\d* \\d*\\s$")
(and be aware that this also matches strings like " 1 " or "1 " or even " ").
I am trying to get a webpage, load it into a string builder, using a BufferedReader and then use a regex to look for and retrieve words or in this case groups of words (department names like computer-science, Electrical-Engineering etc..) that match the regex pattern. I am using the Pattern and Matcher class that java provides but am running into an illegalStateException. I have been staring at this code for quite a while and would like some fresh perspective on what the problem might be. I know it has something to do with the m.find() and m.group() methods. Any help would be greatly appreciated.
I would say from the output I am getting, it recognizes the first words that matches the regex and start throwing illegalStateException after that.
I have also posted my code below:
public class Parser{
static StringBuilder theWebPage;
ArrayList<String> courseNames;
//ArrayList<parserObject> courseObjects;
public static void main(String[] args)
{
Parser p = new Parser();
theWebPage = new StringBuilder();
try {
URL theUrl = new URL("http://ocw.mit.edu/courses/");
BufferedReader reader = new BufferedReader(new InputStreamReader(theUrl.openStream()));
String str = null;
while((str = reader.readLine())!=null)
{
theWebPage.append(" ").append(str);
//System.out.println(theWebPage);
}
//System.out.println(theWebPage);
reader.close();
} catch (MalformedURLException e) {
System.out.println("MalformedURLException");
} catch (IOException e) {
System.out.println("IOException");
}
p.matchString();
}
public Parser()
{
//parserObject courseObject = new parserObject();
//courseObjects = new ArrayList<parserObject>();
courseNames = new ArrayList<String>();
//theWebPage=" ";
}
public void matchString()
{
String matchRegex = "#\\w+(-\\w+)+";
Pattern p = Pattern.compile(matchRegex);
Matcher m = p.matcher(theWebPage);
int i=0;
int x=0;
//m.reset();
while(!(m.matches()))
{
System.out.println("inside matches method " + i);
try{
m.find();
x = m.end();
System.out.println( m.group());
PrintStream out = new PrintStream(new FileOutputStream("/Users/xxxx/Desktop/output.txt"));
System.setOut(out);
//courseNames.add(i,m.group());
i++;
}catch(IllegalStateException e)
{
System.out.println("IllegalStateException");
} catch (FileNotFoundException e) {
System.out.println("FileNotFound Exception");
}
}
}
}
The problem is that you call:
x = m.end();
even though you may not have a match. Why not incorporate your call to find() into your while statement, thereby making it a guard statement also:
while (m.find()) {
Your solution overcomplicates things a bit. How about this?
package MitOpenCourseWareCrawler;
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
import java.net.MalformedURLException;
import java.net.URL;
import java.util.ArrayList;
import java.util.List;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
public class Parser {
private List<String> courseNames = new ArrayList<String>();
private URL url;
public Parser(String url) throws MalformedURLException {
this.url = new URL(url);
}
public static void main(String[] args) throws IOException {
Parser parser = new Parser("http://ocw.mit.edu/courses/");
parser.parse();
for (String courseName : parser.courseNames)
System.out.println(courseName);
}
public void parse() throws IOException {
BufferedReader reader = new BufferedReader(new InputStreamReader(url.openStream()));
Pattern pattern = Pattern.compile(".*<u>(.+)</u>.*");
Matcher matcher;
String line;
while ((line = reader.readLine()) != null) {
matcher = pattern.matcher(line);
if (matcher.matches())
courseNames.add(matcher.group(1));
}
reader.close();
}
}
Besides, I agree with Reimeus that it would probably be a better strategy to use a parsing tool or library than to try and to HTML parsing using regex patterns. But I guess as long as you know the structure of the page and know exactly what you want, a quick'n'dirty solution like yours or mine is okay.