Indexing Android - android

My problem is I have around 1000+ records in an Android App
string field1;
string field2;
string field3;
string field4;
//...
I want to search in this set of records and get the best results on two fields (field1 and field2).
Currently I read each record and compare() (string compare) with the text i want to search so that takes a long time.
What is the best method to perform search?
Store each records in SQLite DB and do "select query where like"
Hash-Mapped
? any other suggestions?
Or may be create an Index of the records and do search.

If you want to search for not exact matches, I would try to make an ArrayList of MyAppRecord where
public class MyAppRecord {
private String record;
private int deviance;
}
and get for each record the deviance of the String you want to find with:
public static int getLevenshteinDistance (String s, String t) {
if (s == null || t == null) {
throw new IllegalArgumentException("Strings must not be null");
}
int n = s.length(); // length of s
int m = t.length(); // length of t
if (n == 0) {
return m;
} else if (m == 0) {
return n;
}
int p[] = new int[n+1]; //'previous' cost array, horizontally
int d[] = new int[n+1]; // cost array, horizontally
int _d[]; //placeholder to assist in swapping p and d
// indexes into strings s and t
int i; // iterates through s
int j; // iterates through t
char t_j; // jth character of t
int cost; // cost
for (i = 0; i<=n; i++) {
p[i] = i;
}
for (j = 1; j<=m; j++) {
t_j = t.charAt(j-1);
d[0] = j;
for (i=1; i<=n; i++) {
cost = s.charAt(i-1)==t_j ? 0 : 1;
// minimum of cell to the left+1, to the top+1, diagonally left and up +cost
d[i] = Math.min(Math.min(d[i-1]+1, p[i]+1), p[i-1]+cost);
}
// copy current distance counts to 'previous row' distance counts
_d = p;
p = d;
d = _d;
}
// our last action in the above loop was to switch d and p, so p now
// actually has the most recent cost counts
return p[n];
}
}
save it to your MyAppRecord-object and finally sort your ArrayList by the deviance of its MyAppRecord-objects.
Note that this could take some time, depending on your set of records. And NOTE that there is no way of telling wether dogA or dogB is on a certain position in your list by searching for dog.
Read up on the Levensthein distance to get a feeling on how it works. You may get the idea of sorting out strings that are possibly to long/short to get a distance that is okay for a threshold you may have.
It is also possible to copy "good enough" results to a different ArrayList.

Related

how to loop through 2d array and make the result appear in table form in android

HI below is the code which gets the four columns data from the curson and put in the 2d array. basically there are two issues one is that i get the last value as nullnullnullnull means all for columns are fetched as null.
the seconds is that i want to print the array in multitextline or if any other widget availabe so that i get four fields in a row. like
id rule_body rule_con boole
0 abc def 1
0 a f 0
c.moveToFirst();
int i=0;
while(c.moveToNext()) {
String id = c.getString(c.getColumnIndex("id"));
String rb = c.getString(c.getColumnIndex("rule_body"));
String cn = c.getString(c.getColumnIndex("rule_cons"));
String bl = c.getString(c.getColumnIndex("boole"));
table[i][0] = id;
table[i][1] = rb;
table[i][2] = cn;
table[i][3] = bl;
++i;
}
for(int a=0;a<count_row;a++)
for(int b=0;b<count_col;b++) {
obj_ml.append(String.valueOf(table[a][b]));
}
so far i am getting all the result in a single line. any help will be appreciated.
Change your for-loop as below
for (int a=0;a<count_row;a++)
{
for(int b=0;b<count_col;b++)
{
obj_ml.append(String.valueOf(table[a][b]));
}
// add to obj_ml new line character '\n'
obj_ml.append("\n");
}

Android - Set text of TextView with Final String Array

I have managed to extract the first letters on a sentence and store that into a variable.
String[] result = matches.toString().split("\\s+");
// The string we'll create
String abbrev = "";
// Loop over the results from the string splitting
for (int i = 0; i < result.length; i++){
// Grab the first character of this entry
char c = result[i].charAt(0);
// If its a number, add the whole number
if (c >= '0' && c <= '9'){
abbrev += result[i];
}
// If its not a number, just append the character
else{
abbrev += c;
}
}
I then store the values into a Final String Array;
List<String> list = Arrays.asList(abbrev);
final String[] cs12 = list.toArray(new String[list.size()]);
I then set the values into a alert dialog as follows:
builder2.setItems(cs12[0].toString().split(","), new DialogInterface.OnClickListener(){
My next task is when the user selects one of the items for it to go into the text view. However it doesn't let me do this.
public void onClick(DialogInterface dialog, int item) {
TextView speechText = (TextView)findViewById(R.id.autoCompleteTextView1);
speechText.setText(Arrays.toString(cs12));
// TextView speechText = (TextView)findViewById(R.id.autoCompleteTextView1);
// speechText.setText(matches.get(item).toString());
However for my other parts matches.get works fine but I cant seem to get cs12.get.
Any Ideas?
Thanks
Use cs12[0].toString().split(",")[item] to show selected item in TextView:
String[] strArr= cs12[0].toString().split(",");
speechText.setText(strArr[item]);

Order object by id in the same order as the ids list

I have list of integer IDs. Lets say this list is ArrayList<Integer> or int[], it doesn't matter. I have another ArrayList<Obj> that contains the objects with the same ids like in the first list, but they are ordered in different order.
I want to order the objects in the second list in the order as the ids in the first list.
EXAMPLE:
FIRST LIST: { 1, 5, 4, 8, 6 }
SECOND LIST: { Obj[id=5], Obj[id=8], Obj[id=6], Obj[id=1], Obj[id=4] }
RESULT LIST: { Obj[id=1], Obj[id=5], Obj[id=4], Obj[id=8], Obj[id=6] }
Can someone tell me an (efficient) way to do this?
I would suggest using a map:
Map<Integer, Obj> map = new HashMap<Integer, Obj>(secondList.size() * 2);
for (final Obj obj : secondList) {
map.put(obj.id, obj);
}
for (int i = 0; i < secondList.size(); i++) {
secondList.set(i, map.get(firstList.get(i)));
}
This runs in O(n), which IMHO is pretty much the best you can get.
A/ Create a matching id index list, such as:
1 -> 0
5 -> 1
4 -> 2
8 -> 3
6 -> 4
That's a reversed reference of your first list. It indicates the position of each id. A SparseIntArray is a good way of doing it:
SparseIntArray ref = new SparseIntArray();
for (int i = 0; i < firstList.size(); i++) {
ref.append(firstList.get(i), i);
}
Then you need to sort your second list using a Comparator that uses the id of the Object and the ref table:
Collections.sort(secondList, new Comparator<Obj>() {
public int compare(Obj t1, Obj t2) {
return ref.get(t1.id) - ref.get(t2.id);
}
});
I was in the middle of writing Etienne's answer when he posted it, so just for fun here's an O(N^2) solution with a smaller constant factor that doesn't create any objects:
int[] first = { 1, 5, 4, 8, 6 };
Obj[] second = { Obj[id=5], Obj[id=8], Obj[id=6], Obj[id=1], Obj[id=4] };
int i = 0;
while(i < second.length) {
int ind = -1;
for(int j=0;j<first.length;j+=1) {
if(first[j] == second[i].id) {
ind = j;
break;
}
}
if(ind == -1) break; //Bad news
if(ind == i) {
i += 1;
} else {
Obj temp = second[i];
second[i] = second[ind];
second[ind] = temp;
}
}
Obviously the creation of second[] is pseudocode, but the rest will work if the arrays are equal length. I think this will be a little bit faster than Etienne's for very small data sets, but you'd have to profile both answers.

Array access producing unwanted result

I am getting an unusual result when attempting to place a value in an array.
I have an array table[] of a simple class result{ int score, long time, string ID}
Intention is to have a sort of leader board.
My code happily finds the correct place to insert a new score if it is in the top 10.
int ix = 0;
int jx = 10; //
while ( ix < jx )
{
if (points > sTable[ix].points)
{
// score is higher move records down
for (jx = mNumRecords - 1; jx >ix ; jx--)
{
sTable[jx] = sTable[jx -1];
}
//now add new score
sTable[ix].score = score; // all good until here
sTable[ix].time = time;
}
ix++;
}
Problem is that when I try to insert the score using sTable[ix].score = score;
The value gets written to sTable[ix].score and also sTable[ix +1].score.
It is repeatable, it occurs at any value of ix, I have single stepped through the code and as far as I can tell the command only executes once.
Has anyone seen this before?
That because you copied the object reference to the next element in the array. You should copy the values, or create a new object:
Option A:
// score is higher move records down
for (jx = mNumRecords - 1; jx >ix ; jx--)
{
sTable[jx].time = sTable[jx -1].time;
sTable[jx].score = sTable[jx -1].score;
}
//now add new score
sTable[ix].score = score; // all good until here
sTable[ix].time = time;
Option B:
for (jx = mNumRecords - 1; jx >ix ; jx--)
{
sTable[jx] = sTable[jx -1];
}
sTable[ix] = new Result(score, time, ""); // Or however you construct the object

Array Being Overwritten with Last Index in Loop

I'm working on code that takes two arrays with strings (the strings are just sentences) and allocates them to classes which are held in another array (The Sentence class array shown below in the code).
So here's my problem. When popList() is called, the for loop runs through twice and works fine, putting the first index of addStrings and addTranslation into the first class in the array. However, when the loop indexes up and runs temp.sentence = addStrings[1] again, it OVERRIDES the first class's .sentence also. Then when temp.translations = addTranslations[1] runs again it OVERRIDES the first class's .translation.
So by the end of the loop, all of the arrays are filled with the same thing: the last index of addStrings and addTranslation. Every time it loops it overwrites all the indices before it with the index it's supposed to be putting in.
Anyone know what the problem is here? Thanks!
public class Sentence {
public String sentence;
public String translation;
Sentence() {
sentence = " ";
translation = " ";
}
}
private void popStrings() {
addStrings[0] = "我是你的朋友。"; addTranslations[0] = "I am your friend.";
addStrings[1] = "你可以帮助我吗?"; addTranslations[1] = "Could you help me?";
addStrings[2] = "我不想吃啊!"; addTranslations[2] = "I don't want to eat!";
}
//Fill Sentence array with string and translation arrays
private void popList() {
int i = 0;
Sentence temp = new Sentence();
for(i = 0; i < addStrings.length && i < addTranslations.length ; i++) {
temp.sentence = addStrings[i];
temp.translation = addTranslations[i];
sentences[i] = temp;
}
}
You need to create new Sentence() inside the loop:
for(i = 0; i < addStrings.length && i < addTranslations.length ; i++) {
Sentence temp = new Sentence();
temp.sentence = addStrings[i];
temp.translation = addTranslations[i];
sentences[i] = temp;
}
Otherwise you set sentence and translation continuously in the same object.

Categories

Resources