File Roster: roster.txt
Reagan rebradshaw835
Ryley rbarber894
Peyton pstott885
Tyrese tmayo945
Caius ccharlton329
The program has to do with exception handling. Problem I am trying to overcome at the moment is being able to get the proper output. I don't know if there is a specific way to find the line that contains the name, and return everything in the line except the name.
so that we are able to return the username assigned.
For example, first line shows:
Reagan rebradshaw835
Method returns just rebradshaw835
Here is the code: (updated code)
vhthanh really helped me to understand how to read from a file!
I decided to edit the code using replace string commands. Without vhthanhI probably wouldn't have learned how to interact with the file.
package chapter11;
import java.util.Scanner;
import java.io.FileInputStream;
import java.io.IOException;
public class LabProgram {
public static String findID(String studentName, Scanner infoScnr) throws Exception {
while (infoScnr.hasNextLine()) {
String line = infoScnr.nextLine();
//String[] values = line.split(" ", 2);
if (line.contains(studentName)) {
line = line.replace(studentName + " ", "");
return line;
}
}
throw new Exception ("Student ID not found for " + studentName);
}
public static String findName(String studentID, Scanner infoScnr) throws Exception {
while (infoScnr.hasNextLine()) {
String line = infoScnr.nextLine();
//String[] values = line.split(" ", 2);
if (line.contains(studentID)) {
line = line.replace(studentID + " ", "");
return line;
}
}
throw new Exception ("Student name not found for " + studentID);
}
public static void main(String[] args) throws IOException {
Scanner scnr = new Scanner(System.in);
String studentName;
String studentID;
String studentInfoFileName;
FileInputStream studentInfoStream = null;
Scanner studentInfoScanner = null;
// Read the text file name from user
studentInfoFileName = scnr.next();
// Open the text file
studentInfoStream = new FileInputStream(studentInfoFileName);
studentInfoScanner = new Scanner(studentInfoStream);
// Read search option from user. 0: findID(), 1: findName()
int userChoice = scnr.nextInt();
// FIXME: findID() and findName() may throw an Exception.
// Insert a try/catch statement to catch the exception and output the exception message.
try {
if (userChoice == 0) {
studentName = scnr.next();
studentID = findID(studentName, studentInfoScanner);
System.out.println(studentID);
}
else {
studentID = scnr.next();
studentName = findName(studentID, studentInfoScanner);
System.out.println(studentName);
}
studentInfoStream.close();
}
catch (Exception exp) {
System.out.println(exp.getMessage());
}
}
}
You need to read the every single line from the Scanner and split() the string into an array of 2 values and then compare it.
Try this code:
public static String findID(String studentName, Scanner infoScnr) throws Exception {
while (infoScnr.hasNextLine()) {
String line = infoScnr.nextLine();
String[] values = line.split(" ", 2);
if (studentName != null && studentName.equals(values[0])) {
return values[1];
}
}
throw new Exception ("Student name not found for " + studentName);
}
public static String findName(String studentID, Scanner infoScnr) throws Exception {
while (infoScnr.hasNextLine()) {
String line = infoScnr.nextLine();
String[] values = line.split(" ", 2);
if (studentID != null && values.length > 1 && studentID.equals(values[1])) {
return values[0];
}
}
throw new Exception ("Student id not found for " + studentID);
}
.split (" ")
for spacing
.split ("/n")
for new line (nextLine)
Related
I was trying to search for the specific data from the text file by using the ID.
But I was just able to search and display for the id T1001.
public static void main(String[] args){
Scanner sc = new Scanner(System.in);
String filepath = "Technician.txt";
System.out.print("Enter ID : ");
String searchTerm= sc.nextLine();
readRecord(searchTerm,filepath);
}
public static void readRecord(String searchTerm,String filepath){
boolean found = false;
String techID="";
String service="";
String firstName="";
String lastName="";
String salary="";
String position="";
String password="";
try
{
Scanner x = new Scanner(new File(filepath));
x.useDelimiter("[\\|]");
while(x.hasNext()&& !found)
{
techID = x.next();
service=x.next();
firstName=x.next();
lastName=x.next();
salary=x.next();
position=x.next();
password=x.next();
if(techID.equals(searchTerm)){
found = true;
}
}
if(found)
{
System.out.print("ID: "+techID+"\n"+"Service : "+service+"\n"+"First Name: "+firstName+"\n"+"Last Name : "+lastName+"\n" + "Salary : "+salary
+"\n" + "Position : "+position);
}
else
{
System.out.print("ID not found");
}
}
catch(Exception e)
{
}
}
And below is my text file :
T1001|Repair|Raymond|Lee|3000.00|staff|abc123|
T1002|Repaint|Joey|Tan|3000.00|staff|123456|
By Default Scanner class takes the first line as input from your file. But you have to read all lines, so its better to use #nextLine method and then #split method to extract your individual values from the line. Follow the bellow code :
import java.util.Scanner;
import java.io.*;
public class example {
public static void main(String[] args){
Scanner sc = new Scanner(System.in);
String filepath = "Technician.txt";
System.out.print("Enter ID : ");
String searchTerm= sc.nextLine();
readRecord(searchTerm,filepath);
}
public static void readRecord(String searchTerm,String filepath){
try
{
Scanner x = new Scanner(new File(filepath));
while(x.hasNext())
{
String values[] = x.nextLine().toString().split("\\|");
if(values[0].equals(searchTerm)){
System.out.print("ID: "+values[0]+"\n"+"Service : "+values[1]+"\n"+"First Name: "+values[2]+"\n"+"Last Name : "+values[3]+"\n" + "Salary : "+values[4]
+"\n" + "Position : "+values[5] + "\n");
return;
}
}
System.out.print("ID not found");
}
catch(Exception e)
{
}
}
}
Reason of your error is that next line also contains string for next line "\n" and that's how techID is read. In my case it looks like "\n\nT1002" . That's why you need to use function contains and if not equals cut your ID. Your code:
public static void readRecord(String searchTerm,String filepath){
boolean found = false;
boolean toUpdate = false;
String techID="";
String service="";
String firstName="";
String lastName="";
String salary="";
String position="";
String password="";
try
{
Scanner x = new Scanner(new File(filepath));
x.useDelimiter("[\\|]");
while(x.hasNext()&& !found)
{
techID = x.next();
service=x.next();
firstName=x.next();
lastName=x.next();
salary=x.next();
position=x.next();
password=x.next();
if(techID.contains(searchTerm)){
found = true;
if(!techID.equals(searchTerm)) {
toUpdate = true;
}
}
}
if(found)
{
if(toUpdate) {
techID = techID.substring(4, techID.length());
}
System.out.print("ID: "+techID+"\n"+"Service : "+service+"\n"+"First Name: "+firstName+"\n"+"Last Name : "+lastName+"\n" + "Salary : "+salary
+"\n" + "Position : "+position);
}
else
{
System.out.print("ID not found");
}
x.close();
}
catch(Exception e)
{
e.printStackTrace();
}
finally {
}
}
}
Another way can be using delimiter two times. Firstly to make rows in result "x" and then make x.split("|") for example.
I'm reading from the file:
name1 wordx wordy passw1
name2 wordx wordy passw2
name3 wordx wordy passw3
name (i) wordx wordy PASSW (i)
x
x word
x words
words
x
words
At the moment I can print line by line:
Line 1: name1 wordx wordy passw1
Line 2: name2 wordx wordy passw2
I plan to have access to:
users [0] = name1
users [1] = name2
users [2] = name3
..
passws [0] = passw1
passws [1] = passw2
passws [2] = passw3
..
My code is:
public static void main(String args[]) throws FileNotFoundException, IOException {
ArrayList<String> list = new ArrayList<String>();
Scanner inFile = null;
try {
inFile = new Scanner(new File("C:\\file.txt"));
} catch (FileNotFoundException e) {
e.printStackTrace();
}
while (inFile.hasNextLine()) {
list.add(inFile.nextLine()+",");
}
String listString = "";
for (String s : list) {
listString += s + "\t";
}
String[] parts = listString.split(",");
System.out.println("Line1: "+ parts[0]);
}
How do I get the following output:
User is name1 and password is passw1
User is name32 and password is passw32
Thanks in advance.
Something like this will do:
public static void main(String args[]) throws FileNotFoundException, IOException {
ArrayList<String> list = new ArrayList<String>();
Scanner inFile = null;
try {
inFile = new Scanner(new File("C:\\file.txt"));
} catch (FileNotFoundException e) {
e.printStackTrace();
}
while (inFile.hasNextLine()) {
list.add(inFile.nextLine());
}
int line = 0;
String[] parts = list.get(line).split(" ");
String username = parts[0];
String pass = parts[3];
System.out.println("Line" + (line + 1) + ": " + "User is " + username +" and password is " + pass);
}
EDIT: if you want to iterate through all lines just put last lines in a loop:
for (int line = 0; line < list.size(); line++) {
String[] parts = list.get(line).split(" ");
String username = parts[0];
String pass = parts[3];
System.out.println("Line" + (line + 1) + ": " + "User is " + username +" and password is " + pass);
}
First thing to do is, to add this loop to the end of your code :
for(int i = 0; i <= parts.length(); i++){
System.out.println("parts["+i+"] :" + parts[i] );
}
that will simply show the result of the split using ,.
Then adapt your code, you may want to use another regex to split() your lines, for instance a space.
String[] parts = listString.split(" ");
for documentation about split() method check this.
If you want to get that output then this should do the trick:
public static void main(String args[]) throws FileNotFoundException, IOException {
Scanner inFile = null;
try {
inFile = new Scanner(new File("F:\\file.txt"));
} catch (FileNotFoundException e) {
e.printStackTrace();
}
Map<String, String> userAndPassMap = new LinkedHashMap<>();
while (inFile.hasNextLine()) {
String nextLine = inFile.nextLine();
String[] userAndPass = nextLine.split(" ");
userAndPassMap.put(userAndPass[0], userAndPass[1]);
}
for (Map.Entry<String, String> entry : userAndPassMap.entrySet()) {
System.out.println("User is:" + entry.getKey() + " and password is:" + entry.getValue());
}
}
By storing in a map you are linking directly each username with its password. If you need to save them into separate arrays then you can do this in the while loop instead:
List<String> users = new LinkedList<>(),passwords = new LinkedList<>();
while (inFile.hasNextLine()) {
String nextLine = inFile.nextLine();
String[] userAndPass = nextLine.split(" ");
users.add(userAndPass[0]);
passwords.add(userAndPass[1]);
}
and later transform them to arrays
users.toArray()
I recommend you use a java.util.Map, a standard API which allows you to store objects and read each one of them by a key. (In your case, string objects indexed by string keys). Example:
Let's assume this empty map:
Map<String, String> map=new HashMap<String,String>();
If you store this:
map.put("month", "january");
map.put("day", "sunday");
You can expect that map.get("month") will return "january", map.get("day") will return "sunday", and map.get(any-other-string) will return null.
Back to your case: First, you must create and populate the map:
private Map<String, String> toMap(Scanner scanner)
{
Map<String, String> map=new HashMap<String, String>();
while (scanner.hasNextLine())
{
String line=scanner.nextLine();
String[] parts=line.split(" ");
// Validation: Process only lines with 4 tokens or more:
if (parts.length>=4)
{
map.put(parts[0], parts[parts.length-1]);
}
}
return map;
}
And then, to read the map:
private void listMap(Map<String,String> map)
{
for (String name : map.keySet())
{
String pass=map.get(name);
System.out.println(...);
}
}
You must include both in your class and call them from the main method.
If you need arbitraray indexing of the read lines, use ArrayList:
First, define a javabean User:
public class User
{
private String name;
private String password;
// ... add full constructor, getters and setters.
}
And then, you must create and populate the list:
private ArrayList<User> toList(Scanner scanner)
{
List<User> list=new ArrayList<User>();
while (scanner.hasNextLine())
{
String line=scanner.nextLine();
String[] parts=line.split(" ");
// Validation: Process only lines with 4 tokens or more:
if (parts.length>=4)
{
list.add(new User(parts[0], parts[parts.length-1]));
}
}
return list;
}
I keep getting an error with my program after it craws the first 2 URL's "Exception in thread "AWT-EventQueue-0" java.lang.StringIndexOutOfBoundsException: String index out of range: 0". The first couple of URL's craw as I want them to and I get the text from them using a method in another class. The other class could be the problem I don't know. Please have a look at my code and see whats happening.
package WebCrawler;
import java.util.Scanner;
import java.util.ArrayList;
import static TextAnalyser.Textanalyser.analyse;
public class Crawler {
public static void main(String[] args) {
// java.util.Scanner input = new java.util.Scanner(System.in);
// System.out.print("Enter a URL: ");
// String url = input.nextLine();
crawler("http://www.port.ac.uk/"); // Traverse the Web from the a starting url
}
public static void crawler(String startingURL) {
ArrayList<String> listOfPendingURLs = new ArrayList<String>();
ArrayList<String> listOfTraversedURLs = new ArrayList<String>();
listOfPendingURLs.add(startingURL);
while (!listOfPendingURLs.isEmpty() && listOfTraversedURLs.size() <= 100) {
String urlString = listOfPendingURLs.remove(0);
if (!listOfTraversedURLs.contains(urlString)) {
listOfTraversedURLs.add(urlString);
String text = urlString;
text = ReadTextfromURL.gettext(text);
text = analyse(text);
System.out.println("text : " + text);
System.out.println("Craw " + urlString);
for (String s: getSubURLs(urlString)) {
if (!listOfTraversedURLs.contains(s)) {
listOfPendingURLs.add(s);
}
}
}
}
}
public static ArrayList<String> getSubURLs(String urlString) {
ArrayList <String> list = new ArrayList<String>();
try {
java.net.URL url = new java.net.URL(urlString);
Scanner input = new Scanner(url.openStream());
int current = 0;
while (input.hasNext()) {
String line = input.nextLine();
current = line.indexOf("http:", current);
while (current > 0) {
int endIndex = line.indexOf("\"", current);
if (endIndex > 0) { // Ensure that a correct URL is found
list.add(line.substring(current, endIndex));
current = line.indexOf("http:", endIndex);
} else {
current = -1;
}
}
}
} catch (Exception ex) {
System.out.println("Error: " + ex.getMessage());
}
return list;
}
}
public class array {
public static void main(String[] args) throws IOException {
BufferedReader reader = new BufferedReader(new FileReader("fruit.txt"));
System.out.println("enter the fruit you want to search");
Scanner input = new Scanner(System.in);
String fruit = input.nextLine();
String line;
List<String> list = new ArrayList<String>();
while((line=reader.readLine()) !=null)
{
list.add(line);
}
reader.close();
for (String s : list) {
System.out.println(s);
}
}
}
I have fruit.txt
apple 20 good
orange 30 good
banana 40 needmore
how do I retrieve how many oranges I have from the array list.
I want the program to read the user input in this case "orange" and display out 30 and the status is not good.
ideal output is
You have orange 30 of them and status is good
Try the following updated class.
public class array
{
public static void main(String[] args) throws IOException
{
BufferedReader reader = new BufferedReader(new FileReader("fruit.txt"));
System.out.println("enter the fruit you want to search");
Scanner input = new Scanner(System.in);
String fruit = input.nextLine();
String line;
boolean found = false;
int count = 0;
List<String> list = new ArrayList<String>();
while ((line = reader.readLine()) != null)
{
String[] items = line.split(" ");
if (fruit.equals(items[0]))
{
found = true;
count = Integer.parseInt(items[1]);
break;
}
list.add(line);
}
reader.close();
if (found)
{
System.out.println("You have " + fruit + " " + count + " of them and status is good");
}
}
}
You need to split your Strings in your List, and then print each elements of your array obtained within your specified string format: -
for (String s : list) {
String[] tokens = s.split(" ");
if (tokens[0].equals(fruit)) {
System.out.println("You have " + tokens[0] + " " + tokens[1] +
" of them and status is " + tokens[2]);
break;
}
}
Or, you can use: -
System.out.format("You have %s %s of them and status is %s",
tokens[0], tokens[1], tokens[2]);
You will need to split up the lines into the three fields using a StringTokenizer. Then I would create a new class to hold that information.
When you read a line, split the values into String array like this:
while((line=reader.readLine()) !=null)
{
String [] values = line.split(" ");
list.add("You have "+values[0] + " " + values[1] " of them and status is "+values[2] );
}
Not tested but should work, try:
public class array {
public static class Fruit {
private String name;
private String count;
private String status;
public Fruit(String name, String count, String status) {
this.name = name;
this.count = count;
this.status = status;
}
public String getName() {
return name;
}
public String getCount() {
return count;
}
public String getStatus() {
return status;
}
}
public static void main(String[] args) throws IOException {
BufferedReader reader = new BufferedReader(new FileReader("fruit.txt"));
System.out.println("enter the fruit you want to search");
Scanner input = new Scanner(System.in);
String fruit = input.nextLine();
String line= "";
HashMap<String, Fruit> map = new HashMap<String, Fruit>();
while ((line = reader.readLine()) != null) {
String[] strings = line.split(" ");
map.put(strings[0], new Fruit(strings[0], strings[1], strings[2]));
}
reader.close();
System.out.print("You have " + fruit + " " + map.get(fruit).getCount() + " of them and status is: " + map.get(fruit).getStatus());
}
}
Here is an error message that keeps coming up as I try to disply results on my program.
Exception in thread "main" java.lang.ArrayIndexOutOfBoundsException: 0
at AddressBookIO.getEntriesString(AddressBookIO.java:38)
at AddressBookEntryApp.main(AddressBookEntryApp.java:42)
I am almost certain my code is correct. My program does everything it is suppose to do except display my results. The ""main" java.lang.ArrayIndexOutOfBoundsException: 0" is the part that confuses me.
Heres the code for AddressBookIO.java, and AddressBookEntryApp
import java.io.*;
public class AddressBookIO
{
private static File addressBookFile = new File("address_book.txt");
private static final String FIELD_SEP = "\t";
private static final int COL_WIDTH = 20;
// use this method to return a string that displays
// all entries in the address_book.txt file
public static String getEntriesString()
{
BufferedReader in = null;
try
{
checkFile();
in = new BufferedReader(
new FileReader(addressBookFile));
// define the string and set a header
String entriesString = "";
entriesString = padWithSpaces("Name", COL_WIDTH)
+ padWithSpaces("Email", COL_WIDTH)
+ padWithSpaces("Phone", COL_WIDTH)
+ "\n";
entriesString += padWithSpaces("------------------", COL_WIDTH)
+ padWithSpaces("------------------", COL_WIDTH)
+ padWithSpaces("------------------", COL_WIDTH)
+ "\n";
// append each line in the file to the entriesString
String line = in.readLine();
while(line != null)
{
String[] columns = line.split(FIELD_SEP);
String name = columns[0];
String emailAddress = columns[1];
String phoneNumber = columns[2];
entriesString +=
padWithSpaces(name, COL_WIDTH) +
padWithSpaces(emailAddress, COL_WIDTH) +
padWithSpaces(phoneNumber, COL_WIDTH) +
"\n";
line = in.readLine();
}
return entriesString;
}
catch(IOException ioe)
{
ioe.printStackTrace();
return null;
}
finally
{
close(in);
}
}
// use this method to append an address book entry
// to the end of the address_book.txt file
public static boolean saveEntry(AddressBookEntry entry)
{
PrintWriter out = null;
try
{
checkFile();
// open output stream for appending
out = new PrintWriter(
new BufferedWriter(
new FileWriter(addressBookFile, true)));
// write all entry to the end of the file
out.print(entry.getName() + FIELD_SEP);
out.print(entry.getEmailAddress() + FIELD_SEP);
out.print(entry.getPhoneNumber() + FIELD_SEP);
out.println();
}
catch(IOException ioe)
{
ioe.printStackTrace();
return false;
}
finally
{
close(out);
}
return true;
}
// a private method that creates a blank file if the file doesn't already exist
private static void checkFile() throws IOException
{
// if the file doesn't exist, create it
if (!addressBookFile.exists())
addressBookFile.createNewFile();
}
// a private method that closes the I/O stream
private static void close(Closeable stream)
{
try
{
if (stream != null)
stream.close();
}
catch(IOException ioe)
{
ioe.printStackTrace();
}
}
// a private method that is used to set the width of a column
private static String padWithSpaces(String s, int length)
{
if (s.length() < length)
{
StringBuilder sb = new StringBuilder(s);
while(sb.length() < length)
{
sb.append(" ");
}
return sb.toString();
}
else
{
return s.substring(0, length);
}
}
}
And
import java.util.Scanner;
public class AddressBookEntryApp
{
public static void main(String args[])
{
// display a welcome message
System.out.println("Welcome to the Address Book application");
System.out.println();
Scanner sc = new Scanner(System.in);
int menuNumber = 0;
while (menuNumber != 3)
{
// display menu
System.out.println("1 - List entries");
System.out.println("2 - Add entry");
System.out.println("3 - Exit\n");
// get input from user
menuNumber = Validator.getIntWithinRange(sc, "Enter menu number: ", 0, 4);
System.out.println();
switch (menuNumber)
{
case 1:
{
String entriesString = AddressBookIO.getEntriesString();
System.out.println(entriesString);
break;
}
case 2:
{
// get data from user
String name = Validator.getRequiredString(sc, "Enter name: ");
String emailAddress = Validator.getRequiredString(sc, "Enter email address: ");
String phoneNumber = Validator.getRequiredString(sc, "Enter phone number: ");
// create AddressBookEntry object and fill with data
AddressBookEntry entry = new AddressBookEntry();
entry.setName(name);
entry.setEmailAddress(emailAddress);
entry.setPhoneNumber(phoneNumber);
AddressBookIO.saveEntry(entry);
System.out.println();
System.out.println("This entry has been saved.\n");
break;
}
case 3:
{
System.out.println("Goodbye.\n");
break;
}
}
}
}
}
The exception means that you are accessing an array's element beyond the size of the array. So, you need to provide the details of your code to be able to let you know the cause of the issue.
It indicates that an array has been accessed with an illegal index. The index is either negative or greater than or equal to the size of the array.
As per your error logs..code at line no:38 in AddressBookIO.java is throwing this exception.
Could be here..
String name = columns[0];
String emailAddress = columns[1];
String phoneNumber = columns[2];
if there is no element at either 0, 1 or 2..
The error message is pretty clear: The 1st element (index 0) of an array with no elements has been incorrectly accessed.
Exception in thread "main" java.lang.ArrayIndexOutOfBoundsException: [index is] 0
For instance, this would throw that exception:
int bad = (new int[0])[0]; // no elements :(
While the following is okay:
int ok = (new int[1])[0]; // one element, can access it!
I suspect it is this:
String[] columns = line.split(FIELD_SEP); // empty array?
String name = columns[0]; // KABOOM!
In any case, check the code on the line reported in the exception.
at AddressBookIO.getEntriesString(AddressBookIO.java:38)
A blank line in 'address_book.txt' perhaps?
You are trying to access the first element of an empty array. It doesn't exist, so you get an exception from the run time.
The array that you are trying to access is the result of the split() method. This will only return an empty array if you pass a string of delimiters: "\t"
So, there must be some lines that contain only tabs with nothing between them.
Instead of using split(), you should consider applying regular expression to each line. This way, you can validate the format of the line and apply "capture groups" at the same time to easily extract values for each field, even if they are empty strings.
Pattern p = Pattern.compile("([^\t]*)\t([^\t]*)\t([^\t]*)");
...
Matcher m = p.matcher(line);
if (!m.matches()) {
/* The line is invalid; skip it or throw an exception. */
...
}
String name = m.group(1);
String emailAddress = m.group(2);
String phoneNumber = m.group(3);
ArrayIndexOutOfBoundsException is thrown when you try to access an Index, which is more than the size of the specified array.
Try to change this :
while(line != null)
{
String[] columns = line.split(FIELD_SEP);
String name = columns[0];
String emailAddress = columns[1];
String phoneNumber = columns[2];
entriesString += padWithSpaces(name, COL_WIDTH) +
padWithSpaces(emailAddress, COL_WIDTH) +
padWithSpaces(phoneNumber, COL_WIDTH) +
"\n";
line = in.readLine();
}
to this :
while(line != null)
{
String[] columns = line.split(FIELD_SEP);
if (columns.length > 2)
{
String name = columns[0];
String emailAddress = columns[1];
String phoneNumber = columns[2];
entriesString += padWithSpaces(name, COL_WIDTH) +
padWithSpaces(emailAddress, COL_WIDTH) +
padWithSpaces(phoneNumber, COL_WIDTH) +
"\n";
}
line = in.readLine();
}