Compare contents of two files line by line - android

public class MainActivity extends Activity {
FileOutputStream fos;
FileInputStream fOne, fTwo;
ArrayList<String> arr1 = new ArrayList<String>();
ArrayList<String> arr2 = new ArrayList<String>();
ArrayList<String> words = new ArrayList<String>();
ArrayList<String> wordsTwo = new ArrayList<String>();
int count = 0;
int countTwo = 0;
int countThree = 0;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
Button fileOne = (Button)findViewById(R.id.file1);
Button fileTwo = (Button)findViewById(R.id.file2);
Button compare = (Button)findViewById(R.id.compare);
arr1.add("1");
arr1.add("2");
arr1.add("3");
arr1.add("4");
//arr1.add("3");
arr2.add("1");
arr2.add("2");
fileOne.setOnClickListener(new OnClickListener() {
#Override
public void onClick(View v) {
// TODO Auto-generated method stub
try
{
fos = openFileOutput("File1", Context.MODE_PRIVATE);
for(int temp = 0; temp< arr1.size(); temp++)
{
fos.write((arr1.get(temp).getBytes()) );
fos.write(System.getProperty("line.separator").getBytes());
}
fos.close();
fos.flush();
}
catch(Exception e)
{
}
}
});
fileTwo.setOnClickListener(new OnClickListener() {
#Override
public void onClick(View v) {
// TODO Auto-generated method stub
try
{
fos = openFileOutput("File2", Context.MODE_PRIVATE);
for(int temp = 0; temp< arr2.size(); temp++)
{
fos.write((arr2.get(temp).getBytes()) );
fos.write(System.getProperty("line.separator").getBytes());
}
fos.close();
fos.flush();
}
catch(Exception e)
{
}
}
});
compare.setOnClickListener(new OnClickListener() {
#Override
public void onClick(View v) {
// TODO Auto-generated method stub
try
{
fOne = openFileInput("File1");
fTwo = openFileInput("File2");
} catch (FileNotFoundException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
Scanner scanFile = new Scanner(new DataInputStream(fOne));
Scanner scanFileT = new Scanner(new DataInputStream(fTwo));
words = new ArrayList<String>();
wordsTwo = new ArrayList<String>();
while (scanFile.hasNextLine())
{
if(scanFile.nextLine()!=null)
{
count++;
}
while(scanFileT.hasNextLine())
{
if(scanFileT.nextLine()!=null)
{
countTwo++;
}
}
}
try
{
fOne.close();
fTwo.close();
scanFile.close();
scanFileT.close();
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
Toast.makeText(getBaseContext(), "One : " + count, 1000).show();
Toast.makeText(getBaseContext(), "Two : " + countTwo, 1000).show();
Toast.makeText(getBaseContext(), "Three : " + countThree, 1000).show();
count = 0 ;
countTwo = 0;
countThree = 0;
}
});
}
}
Above is the code to write and read the file. What I did here, write two files and read the contents..Now I have to compare contents of files line by line. What needs to be done?

Try following code. This will give you desired output. I took files from asset directory. So you need to replace that line of code if you are taking files from other directory.
private void compareFiles() throws Exception {
String s1 = "";
String s2 = "", s3 = "", s4 = "";
String y = "", z = "";
// Reading the contents of the files
BufferedReader br = new BufferedReader(new InputStreamReader(
getAssets().open("first.txt")));
BufferedReader br1 = new BufferedReader(new InputStreamReader(
getAssets().open("second.txt")));
while ((z = br1.readLine()) != null) {
s3 += z;
s3 += System.getProperty("line.separator");
}
while ((y = br.readLine()) != null) {
s1 += y;
s1 += System.getProperty("line.separator");
}
// String tokenizing
StringTokenizer st = new StringTokenizer(s1);
String[] a = new String[10000];
for (int l = 0; l < 10000; l++) {
a[l] = "";
}
int i = 0;
while (st.hasMoreTokens()) {
s2 = st.nextToken();
a[i] = s2;
i++;
}
StringTokenizer st1 = new StringTokenizer(s3);
String[] b = new String[10000];
for (int k = 0; k < 10000; k++) {
b[k] = "";
}
int j = 0;
while (st1.hasMoreTokens()) {
s4 = st1.nextToken();
b[j] = s4;
j++;
}
// comparing the contents of the files and printing the differences, if
// any.
int x = 0;
for (int m = 0; m < a.length; m++) {
if (a[m].equals(b[m])) {
} else {
x++;
Log.d("Home", a[m] + " -- " + b[m]);
}
}
Log.d("Home", "No. of differences : " + x);
if (x > 0) {
Log.d("Home", "Files are not equal");
} else {
Log.d("Home", "Files are equal. No difference found");
}
}
Input File 1
Hi
Hello
Chintan
Rathod
Input File 2
Hi
HellO
Chintan
RathoD
Output
08-26 12:07:58.219: DEBUG/Home(2350): Hello3. -- HellO3.
08-26 12:07:58.219: DEBUG/Home(2350): Rathod -- RathoD
08-26 12:07:58.229: DEBUG/Home(2350): No. of differences : 2
08-26 12:07:58.229: DEBUG/Home(2350): Files are not equal
Edit
To get Difference between two files
Use StringUtils library which is provide by Apache and check this Documentation for more about that library.
And modify following lines of code.
int x = 0;
for (int m = 0; m < a.length; m++) {
if (a[m].equals(b[m])) {
} else {
x++;
Log.d("Home", a[m] + " -- " + b[m]);
//to print difference
if (a[m].length() < b[m].length())
Log.d("Home", "" + StringUtils.difference(a[m], b[m]));
else
Log.d("Home", "" + StringUtils.difference(b[m], a[m]));
}
}
Output
08-26 17:51:26.949: DEBUG/Home(17900): 12 -- 123
08-26 17:51:26.949: DEBUG/Home(17900): Difference String : 3
08-26 17:51:26.949: DEBUG/Home(17900): No. of differences : 1
08-26 17:51:26.949: DEBUG/Home(17900): Files are not equal

Try using java.util.Scanner
while (sc1.hasNext() && sc2.hasNext()) {
String str1 = sc1.next();
String str2 = sc2.next();
if (!str1.equals(str2))
System.out.println(str1 + " != " + str2);
}

Change your while loop to the following:
while (scanFile.hasNextLine() && scanFileT.hasNextLine())
{
if(scanFileT.nextLine().equals(scanFile.nextLine()))
{
// The lines are equal.
} else {
// The lines are not equal.
}
}
if(scanFile.hasNextLine() || scanFileT.hasNextLine())
{
// If more lines remain in one of the files, they are not equal.
} else {
// If no content remains in both files, they are equal.
}
Depending on the size of your file, I would recommend some optimisation like checking the file sizes before you go through them line by line.
The overall logic reads as follows; if both have another line, compare it to see if it is equal. If they don't have another line, check if one of them has lines remaining, if so, they are not equal.
Update
After clarifying the objective of the comparison in chat, see the comments to this question, I have come to the conclusion that another comparison would be more effective and, as a matter of fact, correct. The comparison algorithm above works great if comparing the structure of text but not if comparing a data vector which may or may not be sorted. After some discussion, we came to the conclusion that data needs to be sorted or the comparison will blow the complexity to at least O(n^2)which could be done in O(2n) if the data is sorted. Here the algorithm's skeleton:
if(! scanGroupFriends.hasNextLine())
{
//simple sanity check to see if we need to compare at all. In this case, add all friends.
} else {
String nextFriend = scanGroupFriends.nextLine();
while(scanAllFriends.hasNextLine())
{
if(scanAllFriends.nextLine().equals(nextFriend))
{
// Friend already figures, do not add him and advance the list of group friends.
if(scanGroupFriends.hasNextLine())
{
nextFriend = scanGroupFriends.nextLine();
} else {
// There are no more friends in the group, add all remaining friends to list to show.
break; // Terminate the `while` loop.
}
}
}
}
However, I personally think it is bad to make to many assumptions. What I would suggest is that the friends be saved in a Set, a TreeSet for example. Then, serialize the object rather than manually writing it to file. Sets are neat because they hold several interesting objects. For example, you could easily use the following code to remove all friends in a group from the set of all friends:
allFriends.removeAll(groupFriends);
However, be aware that this removes it from the set completely so you should make a copy beforehand.

Related

Android notifyDataSetChanged not refreshing the items after removing

So I am trying to remove the itempending however it does not remove it from the listview immediately on click. I have to go back and come back to this screen and it will be removed. However my other listview on the same screen was updated immediately (The submitted profile method). I tried to create a method that does the same function I need and call it in before the notifyDataSetChanged but nothing works. Any advise on why my notifyDataSetChanged is not working would be appreciated thanks.
ArrayAdapter<String> adapterSubmit, adapterPending;
ArrayList<String> itemsSubmit, itemsPending;
ListView lstSubmitPro, lstPendingPro;
String path = Environment.getExternalStorageDirectory().getAbsolutePath() + "/CaptureLogs";
Button btnSubmit;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.content_pro_list);
btnSubmit = (Button) findViewById(R.id.btnTest);
lstSubmitPro = (ListView) findViewById(R.id.lstSubmitPro);
lstPendingPro = (ListView) findViewById(R.id.lstPendingPro);
itemsSubmit = new ArrayList<String>();
adapterSubmit = new ArrayAdapter(this, R.layout.prolist, R.id.tvRows, itemsSubmit);
lstSubmitPro.setAdapter(adapterSubmit);
itemsPending = new ArrayList<String>();
adapterPending = new ArrayAdapter(this, android.R.layout.simple_list_item_multiple_choice, itemsPending);
lstPendingPro.setAdapter(adapterPending);
lstPendingPro.setChoiceMode(ListView.CHOICE_MODE_MULTIPLE);
pendingSubmitProfile();
SubmittedProfile();
btnSubmit.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
SparseBooleanArray sp = lstPendingPro.getCheckedItemPositions();
if (sp!= null) {
for (int i = 0; i < sp.size(); i++) {
if (sp.valueAt(i) == true) {
SubmittedProfile();
adapterSubmit.notifyDataSetChanged();
itemsPending.remove(sp.get(i));
adapterPending.notifyDataSetChanged();
Toast.makeText(ProList.this, "Your profiles have been submitted successfully.", Toast.LENGTH_LONG).show();
} else {
Toast.makeText(ProList.this, "Please choose a profile to be submitted.", Toast.LENGTH_LONG).show();
}
}
}
}
});
public void pendingSubmitProfile()
{
File dir = new File(path);
File[] files = dir.listFiles();
for (File f : files) {
if (f.isFile()) {
BufferedReader inputStream = null;
try {
inputStream = new BufferedReader(new FileReader(f));
String lineToRead = "--PENDING SUBMIT--";
String CurrentLine;
while ((CurrentLine = inputStream.readLine()) != null) {
if (CurrentLine.equals(lineToRead)) {
String filen = f.getName().substring(0, f.getName().lastIndexOf("."));
itemsPending.add(filen);
}
}
} catch (IOException e) {
e.printStackTrace();
}
}
}
}
public void SubmittedProfile()
{
File dir = new File(path);
File[] files = dir.listFiles();
for (File f : files) {
if (f.isFile()) {
BufferedReader inputStream = null;
try {
inputStream = new BufferedReader(new FileReader(f));
String lineToRead = "--SUBMITTED--";
String CurrentLine;
while ((CurrentLine = inputStream.readLine()) != null) {
if (CurrentLine.equals(lineToRead)) {
String filen = f.getName().substring(0, f.getName().lastIndexOf("."));
itemsSubmit.add(filen);
}
}
} catch (IOException e) {
e.printStackTrace();
}
}
}
}
LOG
Before, 2 items but 1 checked
05-02 08:00:02.409 4293-4293/com.example.irambi.irmobilewizard D/returned value:: 2 1 2
After, 2 items but 1 checked
05-02 08:00:03.726 4293-4293/com.example.irambi.irmobilewizard D/returned value:: 0 1 0
This is for 1 item and 1 checked. I cannot tell if this is before or after since theres only 1 printed on logcat. This will crash and error is as follows
05-02 08:03:35.345 4293-4293/com.example.irambi.irmobilewizard D/returned value:: 1 1 1
java.lang.IndexOutOfBoundsException: Invalid index 0, size is 0
Before, 2 items but 2 checked
05-02 08:07:56.378 4596-4596/com.example.irambi.irmobilewizard D/returned value:: 2 2 2
After, 2 items but 2 checked - This will crash
05-02 08:07:57.671 4596-4596/com.example.irambi.irmobilewizard D/returned value:: 0 2 0
java.lang.IndexOutOfBoundsException: Invalid index 1, size is 0
All the testing are done using
itemsPending.remove(sp.keyAt(i));
adapterPending.remove(adapterPending.getItem(sp.keyAt(i)));
Log based on:
Log.d("returned value:", itemsPending.size() + " " + sp.size() + " " + adapterPending.getCount());
Try this one
itemsPending.remove(sp.keyAt(i));
adapterPending.remove(adapterPending.getItem(sp.keyAt(i)));
adapterPending.notifyDataSetChanged();
EDIT:
So basically the switching of list data is working fine. What's messing the code is his file writing. I resolve it this way.
First is a create a function that would update my Pending Files to submitted.
public void submitPendingProfile(String filename){
try {
BufferedReader file = new BufferedReader(new FileReader(path + "/" + filename+".txt"));
String line;
StringBuffer inputBuffer = new StringBuffer();
while ((line = file.readLine()) != null) {
inputBuffer.append(line);
inputBuffer.append('\n');
}
String inputStr = inputBuffer.toString();
file.close();
inputStr = inputStr.replace("--PENDING SUBMIT--", "--SUBMITTED--");
FileOutputStream fileOut = new FileOutputStream(path + "/" + filename+".txt");
fileOut.write(inputStr.getBytes());
fileOut.close();
} catch (Exception e) {
System.out.println("Problem reading file.");
}
}
Then i refactor the loop for simplier process. Like removing the line SubmittedProfile(); that keeps reading all text files if conditions is true. That is a lot of process. Here's how instead.
for(int i = lstPendingPro.getAdapter().getCount() - 1 ; i >= 0; i--) {
if (sp.get(i)) {
//So when file is submitted, i update the files status using the above function.
submitPendingProfile(itemsPending.get(i));
//To avoid rereading of files, just add the item before removing it to the pending list
itemsSubmit.add(itemsPending.get(i));
adapterSubmit.notifyDataSetChanged();
itemsPending.remove(sp.keyAt(i));
adapterPending.notifyDataSetChanged();
Toast.makeText(ProList.this, "Your profiles have been submitted successfully.", Toast.LENGTH_LONG).show();
}
}
Did You tried changing your code to this order
btnSubmit.setOnClickListener(new View.OnClickListener()
{
#Override
public void onClick (View v){
SparseBooleanArray sp = lstPendingPro.getCheckedItemPositions();
if (sp != null) {
for (int i = 0; i < sp.size(); i++) {
if (sp.valueAt(i) == true) {
SubmittedProfile();
itemsPending.remove(sp.get(i));
Toast.makeText(ProList.this, "Your profiles have been submitted successfully.", Toast.LENGTH_LONG).show();
} else {
Toast.makeText(ProList.this, "Please choose a profile to be submitted.", Toast.LENGTH_LONG).show();
}
}
}
adapterSubmit.notifyDataSetChanged();
adapterPending.notifyDataSetChanged();
}
});
Try this code..
itemsPending.remove(itemsPending.indexOf(sp.get(i)));
adapterPending.notifyDataSetChanged();
itemsPending.remove(sp.get(i));
adapterPending.notifyDataSetChanged();
listview.invalidate();
Try above code might be it will help you.

Why I can't send a large amount of data via Bluetooth Android?

I'm still newbie and I need help to coding my Android Studio >0<
I can't to send a long data, although I change the size of "buffer". What should I do ?
This is the receiver program :
public void run() {
InputStream inputStream;
try {
inputStream = mBTSocket.getInputStream();
while (!bStop) {
byte[] buffer = new byte[1024];
if (inputStream.available() > 0)
{
inputStream.read(buffer);
int i = 0;
/*
* This is needed because new String(buffer) is taking the entire buffer i.e. 256 chars on Android 2.3.4 http://stackoverflow.com/a/8843462/1287554
*/
for (i = 0; i < buffer.length && buffer[i] != 0; i++) {}
final String strInput = new String(buffer, 0, i);
/*
* If checked then receive text, better design would probably be to stop thread if unchecked and free resources, but this is a quick fix
*/
}
Thread.sleep(500);
}
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
This are the sender program :
public void sendStringBT(String s)
{
try {
mBTSocket.getOutputStream().write(s.getBytes());
sleep();
Toast.makeText(getApplicationContext(), "Sent...", Toast.LENGTH_SHORT).show();
mBTSocket.getOutputStream().flush();
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
This is how to we call to send data :
sendStringBT(dataPage6); //send data via Bluetooth
I think the problem is in the design of the receiver (using Sleep in an endless cycle ...) I Solved BTL communication in .net Xamarin, but the principle should be the same.
Reading from btlInputStream must be quick and can not use sleep. You use an endless cycle, reading in buffer (OK). Immediately a dune bytes to an auxiliary large buffer (use read / write cursor) and then, for example, in timer treat the data (I suppose you are using some packet protocol)
while (ContinueCycle)
{
int rxlen;
lock (InternalBufferReadLock)
{//Pouze rychle prectu a schovam si do pole
rxlen = USBConnection.BulkTransfer(USBEndPointRead, InternalBufferRead, InternalBufferRead.Length, 0);
Array.Copy(InternalBufferRead, TempBufferRead, rxlen);
}
lock (BufferReadLock)
{
for (int i = 2; i < rxlen; i++)
{
BufferRead[BufferReadWriteCursor] = TempBufferRead[i];
BufferReadWriteCursor++;
}
}
}
and in timer save it to MainBuffer from which the data is processing
if (tmpWriteCursor > tmpReadCursor)
{
lock (BufferReadLock)
{
int newBytes = tmpWriteCursor - tmpReadCursor;
for (int i = 0; i < newBytes; i++)
{
BufferReadMain[BufferReadReadCursor] = BufferRead[BufferReadReadCursor++];
}
}
}
...
bool newline = false;
string tmpRadek = "";
int lastLineIndex = 0;
List<string> list = new List<string>();
for (int i = LastWriteLineIndex; i < tmpWriteCursor; i++)
{
if (BufferReadMain[i] >= 32 && BufferReadMain[i] <= 255)
{
tmpRadek += (char)BufferReadMain[i];
}
else if (BufferReadMain[i] == 13) newline = true;
else if (BufferReadMain[i] == 10)
{
if (newline)
{
newline = false;
list.Add(Utils.GetFormatedDateTime(DateTime.Now) + " " + tmpRadek);
tmpRadek = "";
lastLineIndex = i + 1;
}
}
else
{
tmpRadek += "?" + BufferReadMain[i].ToString() + "?";
}
}

receive a string message from user input in android and parse to an int so can be stored in an array and compared with another array of integers

I am having a problem with the above task in my android application. I am accepting user input from the EditText widget in the form of String. I accepting numbers from the user so I have to parse them to integers so they can be compared with another array of integers. I have the line:
String message = editText.getText().toString()
then to try and parse the String to an int I have the code line:
int userNumbers = Integer.parseInt(message).
However when I attempt to compare the array userArray with the array numbers I am getting the error that "Incompatible operand types String and Integer.
Can anyone see where my problem is or how I can solve it? Here's my code:
Thanks in advance.
public class MainActivity extends Activity {
public final static String EXTRA_MESSAGE = ".com.example.lotterychecker.MESSAGE";
static boolean bonus = false;
static boolean jackpot = false;
static int lottCount = 0;
Button check;
Integer [] numbers;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
//link to the intended web site and get the lottery numbers while the app is opening
try {
Document doc = Jsoup.connect("http://www.national-lottery.co.uk/player/p/drawHistory.do").userAgent("Mozilla").get();
Elements elements = doc.getElementsByClass("drawhistory");
Element table = elements.first();
Element tbody = table.getElementsByTag("tbody").first();
Element firstLottoRow = tbody.getElementsByClass("lottorow").first();
Element dateElement = firstLottoRow.child(0);
System.out.println(dateElement.text());
Element gameElement = firstLottoRow.child(1);
System.out.println(gameElement.text());
Element noElement = firstLottoRow.child(2);
System.out.println(noElement.text());
String [] split = noElement.text().split(" - ");
// set up an array to store numbers from the latest draw on the lottery web page
Integer [] numbers = new Integer [split.length];
int i = 0;
for (String strNo : split) {
numbers [i] = Integer.valueOf(strNo);
i++;
}
for (Integer no : numbers) {
System.out.println(no);
}
Element bonusElement = firstLottoRow.child(3);
Integer bonusBall = Integer.valueOf(bonusElement.text());
System.out.println("Bonus ball: " + bonusBall);
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
#Override
public boolean onCreateOptionsMenu(Menu menu) {
// Inflate the menu; this adds items to the action bar if it is present.
getMenuInflater().inflate(R.menu.main, menu);
return true;
}
//called when the user clicks the send button
public void checkNumbers(View view) {
final int SIZE =6;
String [] userArray = new String[SIZE];
//create an intent to display the numbers
Intent intent = new Intent(this, DisplayNumbersActivity.class);
EditText editText = (EditText) findViewById(R.id.enter_numbers);
String message = editText.getText().toString();
intent.putExtra(EXTRA_MESSAGE, message );
startActivity(intent);
//parse string message to an int for user numbers
try{
int userNumbers = Integer.parseInt(message); //is this right?
}//try
catch (NumberFormatException e)
{
System.out.println("Not a number" + e.getMessage());
}
Toast.makeText(MainActivity.this, "Here are your numbers", Toast.LENGTH_LONG).show();
for (int count =0; count < SIZE; count ++)
{
if (check.isPressed())
{
userArray[count] = editText.getText().toString();
}
}//for
//compare the two arrays of integers
for (int loop = 0; loop < userArray.length; loop++)
{
for (int loopOther = 0; loopOther < numbers.length; loopOther++)
{
if (userArray[loop] == numbers[loopOther]) //how do I parse this?
{
lottCount++;
}else if (userArray[loop] == bonus)
{
bonus = true;
}
}//for
}//for main
You have this
Integer [] numbers; // numbers is an integer array
You have string array
String [] userArray = new String[SIZE]; // userArray is a string array
You compare like below
if (userArray[loop] == numbers[loopOther])
So you get the error Incompatible operand types String and Integer.
try
if (Integer.parseInt(userArray[loop]) == numbers[loopOther])
Enclosing the above with try catch block
String message = editText.getText().toString();
try{
int userNumbers = Integer.parseInt(message);
//is this right? yes
}
catch (NumberFormatException e)
{
e.printStacktrace();
}
Change String to Int here:
for (int loop = 0; loop < userArray.length; loop++)
{
for (int loopOther = 0; loopOther < numbers.length; loopOther++)
{
if (Integer.valueOf(userArray[loop]) == numbers[loopOther]) //how do I parse this?
{
lottCount++;
}else if (Integer.valueOf(userArray[loop]) == bonus)
{
bonus = true;
}
}//for
}//for main
Parse Like this :
for (int loop = 0; loop < userArray.length; loop++)
{
for (int loopOther = 0; loopOther < numbers.length; loopOther++)
{
if (Integer.parseInt(userArray[loop]) == numbers[loopOther])
{
lottCount++;
}else if (userArray[loop] == bonus)
{
bonus = true;
}
}
}

NFC tag reading problem

This is my code to read the NFC tag. Why authentication is failing always? It is detecting the card but not reading the data. Could you please help me? Why if block is not executing? Where i'am wrong?
void resolveIntent(Intent intent)
{
String action = intent.getAction();
if (NfcAdapter.ACTION_TECH_DISCOVERED.equals(action))
{
Tag tagFromIntent = intent.getParcelableExtra(NfcAdapter.EXTRA_TAG);
MifareClassic mfc = MifareClassic.get(tagFromIntent);
byte[] data;
try
{
mfc.connect();
boolean auth = false;
String cardData = "";
int sectorCount = mfc.getSectorCount();
int blockCount = 0;
int blockIndex = 0;
for(int j = 0; j < sectorCount; j++)
{
auth = mfc.authenticateSectorWithKeyA(j, MifareClassic.KEY_DEFAULT);
if(auth)
{
blockCount = mfc.getBlockCountInSector(j);
blockIndex = 0;
for(int i = 0; i < blockCount; i++)
{
blockIndex = mfc.sectorToBlock(j);
data = mfc.readBlock(blockIndex);
cardData = cardData + getHexString(data, data.length);
blockIndex++;
}
}
else
{
// Authentication failed - Handle it
showAlert(AUTH); //this alert message is executing always
}
}
Toast.makeText(getApplicationContext(), cardData, Toast.LENGTH_LONG).show();
}
catch (IOException e)
{
Log.e(TAG, e.getLocalizedMessage());
showAlert(NETWORK);
}
}//end of if
}// End of method
Since it is not a new tag, and has been written by another app, I would suspect that the authentication key has changed. You are using the default keys, but the other app may have changed them. The older Nokia phones do this all the time. In that case instead of using MifareClasic.KEY_DEFAULT, you will need to figure out what the new key is for keyA
Try to use MifareClassic.KEY_NFC_FORUM as the keyA.

I'm not understanding the following code

I have to understand this code to create my own app(almost based on this function):
public static String[][] ReadFilePerLine(Context context, String nom) {
int i = 0;
try {
FileInputStream fIn = context.openFileInput(nom);
InputStreamReader ipsr = new InputStreamReader(fIn);
BufferedReader b = new BufferedReader(ipsr);
i = getLineNumber(context, nom);
String[][] s = new String[2][i/2];
i = 0;
String ligne;
int j = 0;
while ((ligne = b.readLine()) != null) {
if (i % 2 == 0)
s[0][j] = ligne;
else {
s[1][j] = ligne;
j++;
}
i++;
}
fIn.close();
ipsr.close();
return s;
}
catch (Exception e)
{}
I'm not understanding why the using of a 2D array? and with two rows ?(String[][] s = new String[2][i/2];)
here is the data that it will be stored in the file:
data = date + " : " + y + "L/100KM"+ " " + value1 + "L "+ value2 + "KM\n";
Necessary functions:
public void updatelv(Activity activity) {
SharedPreferences preferences = PreferenceManager.getDefaultSharedPreferences(context);
String fileName = getResources().getString(R.string.fileName);
fileDir = "" + preferences.getString("login", "") + "."+ preferences.getString("marque", "") + ".";
s = myIO.ReadFilePerLine(getApplicationContext(), fileDir+fileName);
ListView L = (ListView) findViewById(R.id.lv);
L.setAdapter(new ArrayAdapter<String>(this, R.layout.list_item, s[0]));
for (int i = 0; i< s[0].length; i++) {
Log.d("Saves",s[0][i]);
}
}
#Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.histo);
context = getApplicationContext();
activity = this;
final SharedPreferences preferences = PreferenceManager
.getDefaultSharedPreferences(context);
String fileName = getResources().getString(R.string.fileName);
fileDir = "" + preferences.getString("login", "") + "."+ preferences.getString("marque", "") + ".";
s = myIO.ReadFilePerLine(getApplicationContext(), fileDir + fileName);
updatelv(this);
ListView L = (ListView) findViewById(R.id.lv);
L.setTextFilterEnabled(true);
L.setOnItemClickListener(new OnItemClickListener() {
#Override
public void onItemClick(AdapterView<?> parent, View view,
int position, long id) {
// When clicked, show a toast with the TextView text
String tmp = s[1][position];
if (tmp == null)
tmp = "Aucun fichier trouvé!";
Toast.makeText(getApplicationContext(), tmp, Toast.LENGTH_SHORT)
.show();
}
});
ReadFilePerLine function:
public static String[][] ReadFilePerLine(Context context, String nom) {
int i = 0;
try {
FileInputStream fIn = context.openFileInput(nom);
InputStreamReader ipsr = new InputStreamReader(fIn);
BufferedReader b = new BufferedReader(ipsr);
i = getLineNumber(context, nom);
String[][] s = new String[2][i/2];
i = 0;
String ligne;
int j = 0;
while ((ligne = b.readLine()) != null) {
if (i % 2 == 0)
s[0][j] = ligne;
else {
s[1][j] = ligne;
j++;
}
i++;
}
fIn.close();
ipsr.close();
return s;
}
catch (Exception e)
{
}
Thank you for you help.
The code is clearly reading from a file whose format consists of pairs of lines; it puts the first line of each pair in s[0][...] and the second line of each pair in s[1][...]. If your format doesn't have that peculiarity -- which it doesn't sound as if it does -- then you don't need to do that. Just make an ordinary 1-dimensional array of Strings.
It appears that what they are doing is breaking the file down into two lists (or String arrays, in this case), one which contains all the even-numbered lines, and one which contains all the odd-numbered lines. I'll comment up the code for you:
public static String[][] ReadFilePerLine(Context context, String nom) {
int i = 0;
try {
//open the specified input file and create a reader
FileInputStream fIn = context.openFileInput(nom);
InputStreamReader ipsr = new InputStreamReader(fIn);
BufferedReader b = new BufferedReader(ipsr);
//get the total number of lines in the file, and allocate
//a buffer large enough to hold them all
i = getLineNumber(context, nom);
String[][] s = new String[2][i/2];
i = 0; //set the current line to 0
String ligne;
int j = 0; //set the section index to 0
//now read through the lines in the file, and place every
//even-numbered line in the first section ('s[0]'), and every
//odd-numbered line in the second section ('s[1]')
while ((ligne = b.readLine()) != null) {
if (i % 2 == 0)
//even-numbered line, it goes into the first section
s[0][j] = ligne;
else {
//odd-numbered line, it goes into the second section
s[1][j] = ligne;
j++; //increment the section index
}
i++; //increment the line count
}
//done, cleanup and return
fIn.close();
ipsr.close();
return s;
}
catch (Exception e) {
//should at least log an error here...
}
}
As to why they chose to use a String[][], I cannot say. Probably for convenience, since they want a single object that they can return from this function that contains both lists. Personally I would use a Map that has two List instances in it, but the String[][] works just as well and is probably marginally more efficient.
Judging from your example data it does not appear that you need to use this format. But if you want to use it, you need to structure your data so that the key is on one line, and its associated value is on the next, like:
date
2011-03-19
userName
someGuy
it seems to read from a file, split it into the two dimensional array (based on row count).
Why it does it? I have no idea why you'd want that. Check out the function that it returns s to and find out!

Categories

Resources