diff options
Diffstat (limited to 'app/src')
-rwxr-xr-x | app/src/main/java/org/rssin/neurons/FeedSorter.java | 133 | ||||
-rwxr-xr-x | app/src/main/java/org/rssin/neurons/Feedback.java | 16 | ||||
-rwxr-xr-x | app/src/main/java/org/rssin/neurons/MultiNeuralNetwork.java | 5 | ||||
-rwxr-xr-x | app/src/main/java/org/rssin/neurons/MultiNeuralNetworkPrediction.java | 10 | ||||
-rwxr-xr-x | app/src/main/java/org/rssin/neurons/NeuralNetwork.java | 5 | ||||
-rwxr-xr-x | app/src/main/java/org/rssin/neurons/NeuralNetworkPrediction.java | 4 | ||||
-rwxr-xr-x | app/src/main/java/org/rssin/neurons/Neuron.java | 1 | ||||
-rwxr-xr-x | app/src/main/java/org/rssin/neurons/PredictionInterface.java | 1 | ||||
-rwxr-xr-x | app/src/main/java/org/rssin/neurons/TrainingCase.java | 26 | ||||
-rw-r--r-- | app/src/main/java/org/rssin/rss/Feed.java | 223 | ||||
-rw-r--r-- | app/src/main/java/org/rssin/rss/FeedItem.java | 8 | ||||
-rw-r--r-- | app/src/main/java/org/rssin/rss/FeedLoader.java | 224 | ||||
-rwxr-xr-x | app/src/main/java/org/rssin/rssin/FeedLoaderAndSorter.java | 64 | ||||
-rwxr-xr-x[-rw-r--r--] | app/src/main/java/org/rssin/rssin/Filter.java | 9 |
14 files changed, 582 insertions, 147 deletions
diff --git a/app/src/main/java/org/rssin/neurons/FeedSorter.java b/app/src/main/java/org/rssin/neurons/FeedSorter.java index 550d9e5..157a8f7 100755 --- a/app/src/main/java/org/rssin/neurons/FeedSorter.java +++ b/app/src/main/java/org/rssin/neurons/FeedSorter.java @@ -5,7 +5,9 @@ import android.gesture.Prediction; import org.rssin.rss.FeedItem;
import java.io.IOException;
+import java.io.Serializable;
import java.util.ArrayList;
+import java.util.Arrays;
import java.util.Calendar;
import java.util.Collection;
import java.util.Collections;
@@ -18,39 +20,43 @@ import java.util.TimeZone; /**
* Created by Jos on 14-5-2015.
*/
-public class FeedSorter {
+public class FeedSorter implements Serializable{
+ private static final long serialVersionUID = 0;
+
+ private final int MAX_TRAINING_HISTORY = 250;
private final int SECONDS_IN_DAY = 24 * 60 * 60;
private MultiNeuralNetwork nn = new MultiNeuralNetwork(25, 50);
+ private List<TrainingCase> trainingCases = new ArrayList<>();
+
private int[] isNthMonthInput = new int[12];
private int[] isNthWeekDayInput = new int[7];
private int isMorning, isAfternoon, isEvening, isNight, biasInput;
private Hashtable<String, Integer> categoryInputs = new Hashtable<String, Integer>();
- private Hashtable<String, Integer> wordInputs = new Hashtable<String, Integer>();
- private Hashtable<String, Integer> feedSourceInputs = new Hashtable<String, Integer>();
+ //private Hashtable<String, Integer> wordInputs = new Hashtable<String, Integer>();
+ //private Hashtable<String, Integer> feedSourceInputs = new Hashtable<String, Integer>();
public FeedSorter() {
- //TODO: Load Neural Network
createNewNetwork();
}
private void createNewNetwork() {
biasInput = nn.addInput();
-// for(int i = 0; i < 12; i++)
-// {
-// isNthMonthInput[i] = nn.addInput();
-// }
-//
-// for(int i = 0; i < 7; i++)
-// {
-// isNthWeekDayInput[i] = nn.addInput();
-// }
-//
-// isMorning = nn.addInput();
-// isAfternoon = nn.addInput();
-// isEvening = nn.addInput();
-// isNight = nn.addInput();
+ for(int i = 0; i < 12; i++)
+ {
+ isNthMonthInput[i] = nn.addInput();
+ }
+
+ for(int i = 0; i < 7; i++)
+ {
+ isNthWeekDayInput[i] = nn.addInput();
+ }
+
+ isMorning = nn.addInput();
+ isAfternoon = nn.addInput();
+ isEvening = nn.addInput();
+ isNight = nn.addInput();
}
private PredictionInterface getPrediction(FeedItem item) {
@@ -75,39 +81,39 @@ public class FeedSorter { }
//Set month
-// Calendar cal = Calendar.getInstance(TimeZone.getTimeZone("UTC"));
-// for(int i = 0; i < isNthMonthInput.length; i++)
-// {
-// if(cal.get(Calendar.MONTH) - cal.getMinimum(Calendar.MONTH) == i)
-// {
-// inputs[isNthMonthInput[i]] = 1;
-// }
-// }
+ Calendar cal = Calendar.getInstance(TimeZone.getTimeZone("UTC"));
+ for(int i = 0; i < isNthMonthInput.length; i++)
+ {
+ if(cal.get(Calendar.MONTH) - cal.getMinimum(Calendar.MONTH) == i)
+ {
+ inputs[isNthMonthInput[i]] = 1;
+ }
+ }
//Set weekday
-// for(int i = 0; i < isNthWeekDayInput.length; i++)
-// {
-// if(cal.get(Calendar.DAY_OF_WEEK) - cal.getMinimum(Calendar.DAY_OF_WEEK) == i)
-// {
-// inputs[isNthMonthInput[i]] = 1;
-// }
-// }
+ for(int i = 0; i < isNthWeekDayInput.length; i++)
+ {
+ if(cal.get(Calendar.DAY_OF_WEEK) - cal.getMinimum(Calendar.DAY_OF_WEEK) == i)
+ {
+ inputs[isNthMonthInput[i]] = 1;
+ }
+ }
//Set day
-// int hourOfDay = cal.get(Calendar.HOUR_OF_DAY);
-// if(hourOfDay > 6 && hourOfDay < 12)
-// {
-// inputs[isMorning] = 1;
-// }else if(hourOfDay >= 12 && hourOfDay <= 6)
-// {
-// inputs[isAfternoon] = 1;
-// }else if(hourOfDay >= 6 && hourOfDay < 23)
-// {
-// inputs[isEvening] = 1;
-// }else if(hourOfDay >= 23 || hourOfDay <= 6)
-// {
-// inputs[isNight] = 1;
-// }
+ int hourOfDay = cal.get(Calendar.HOUR_OF_DAY);
+ if(hourOfDay > 6 && hourOfDay < 12)
+ {
+ inputs[isMorning] = 1;
+ }else if(hourOfDay >= 12 && hourOfDay <= 6)
+ {
+ inputs[isAfternoon] = 1;
+ }else if(hourOfDay >= 6 && hourOfDay < 23)
+ {
+ inputs[isEvening] = 1;
+ }else if(hourOfDay >= 23 || hourOfDay <= 6)
+ {
+ inputs[isNight] = 1;
+ }
for(String category : item.getCategory())
{
@@ -126,16 +132,31 @@ public class FeedSorter { public void feedback(FeedItem item, Feedback feedback)
{
PredictionInterface prediction = getPrediction(item);
- switch(feedback)
+ prediction.learn(feedback.toExpectedOutput());
+ trainingCases.add(new TrainingCase(prediction.getInputs(), feedback));
+
+ while(trainingCases.size() > MAX_TRAINING_HISTORY)
+ {
+ trainingCases.remove(0);
+ }
+ }
+
+ /**
+ * Runs an iteration of training, using feedback that was provided previously using FeedSorter.feedback(...).
+ */
+ public void train()
+ {
+ for(TrainingCase t : trainingCases)
{
- case Like:
- prediction.learn(1);
- break;
- case Dislike:
- prediction.learn(-1);
- break;
- default:
- throw new IllegalArgumentException("feedback");
+ double[] inputs = t.getInputs();
+ if(inputs.length < nn.getInputCount())
+ {
+ // Resize array to fit new input size
+ inputs = Arrays.copyOf(inputs, nn.getInputCount());
+ }
+
+ PredictionInterface prediction = nn.computeOutput(inputs);
+ prediction.learn(t.getFeedback().toExpectedOutput());
}
}
diff --git a/app/src/main/java/org/rssin/neurons/Feedback.java b/app/src/main/java/org/rssin/neurons/Feedback.java index af5f1b3..9652b2b 100755 --- a/app/src/main/java/org/rssin/neurons/Feedback.java +++ b/app/src/main/java/org/rssin/neurons/Feedback.java @@ -4,6 +4,18 @@ package org.rssin.neurons; * Created by Jos on 19-5-2015.
*/
public enum Feedback {
- Like,
- Dislike
+ Like, Dislike;
+
+ double toExpectedOutput()
+ {
+ switch(this)
+ {
+ case Like:
+ return 1;
+ case Dislike:
+ return -1;
+ default:
+ throw new IllegalArgumentException();
+ }
+ }
}
diff --git a/app/src/main/java/org/rssin/neurons/MultiNeuralNetwork.java b/app/src/main/java/org/rssin/neurons/MultiNeuralNetwork.java index 50fa707..a2f06eb 100755 --- a/app/src/main/java/org/rssin/neurons/MultiNeuralNetwork.java +++ b/app/src/main/java/org/rssin/neurons/MultiNeuralNetwork.java @@ -1,9 +1,12 @@ package org.rssin.neurons;
+import java.io.Serializable;
+
/**
* Created by Jos on 14-5-2015.
*/
-class MultiNeuralNetwork {
+class MultiNeuralNetwork implements Serializable{
+ private static final long serialVersionUID = 0;
private NeuralNetwork[] networks;
public MultiNeuralNetwork(int numNetworks, int numHiddenNodes) {
diff --git a/app/src/main/java/org/rssin/neurons/MultiNeuralNetworkPrediction.java b/app/src/main/java/org/rssin/neurons/MultiNeuralNetworkPrediction.java index 8df99e5..dc85261 100755 --- a/app/src/main/java/org/rssin/neurons/MultiNeuralNetworkPrediction.java +++ b/app/src/main/java/org/rssin/neurons/MultiNeuralNetworkPrediction.java @@ -7,6 +7,11 @@ class MultiNeuralNetworkPrediction implements PredictionInterface { private PredictionInterface[] predictions;
MultiNeuralNetworkPrediction(PredictionInterface[] predictions)
{
+ if(predictions.length <= 0)
+ {
+ throw new IllegalArgumentException("predictions");
+ }
+
this.predictions = predictions;
}
@@ -27,4 +32,9 @@ class MultiNeuralNetworkPrediction implements PredictionInterface { prediction.learn(expectedOutput);
}
}
+
+ public double[] getInputs()
+ {
+ return predictions[0].getInputs();
+ }
}
diff --git a/app/src/main/java/org/rssin/neurons/NeuralNetwork.java b/app/src/main/java/org/rssin/neurons/NeuralNetwork.java index 7c2e447..620d5bd 100755 --- a/app/src/main/java/org/rssin/neurons/NeuralNetwork.java +++ b/app/src/main/java/org/rssin/neurons/NeuralNetwork.java @@ -1,9 +1,12 @@ package org.rssin.neurons;
+import java.io.Serializable;
+
/**
* Created by Jos on 14-5-2015.
*/
-class NeuralNetwork {
+class NeuralNetwork implements Serializable{
+ private static final long serialVersionUID = 0;
private Neuron[] hiddenNodes;
private Neuron outputNode;
diff --git a/app/src/main/java/org/rssin/neurons/NeuralNetworkPrediction.java b/app/src/main/java/org/rssin/neurons/NeuralNetworkPrediction.java index 162ba21..9d6fc89 100755 --- a/app/src/main/java/org/rssin/neurons/NeuralNetworkPrediction.java +++ b/app/src/main/java/org/rssin/neurons/NeuralNetworkPrediction.java @@ -16,11 +16,11 @@ class NeuralNetworkPrediction implements PredictionInterface { this.nn = nn;
}
- double[] getInputs() {
+ public double[] getInputs() {
return inputs;
}
- double[] getIntermediateValues() {
+ public double[] getIntermediateValues() {
return intermediateValues;
}
diff --git a/app/src/main/java/org/rssin/neurons/Neuron.java b/app/src/main/java/org/rssin/neurons/Neuron.java index 5df9d47..724732d 100755 --- a/app/src/main/java/org/rssin/neurons/Neuron.java +++ b/app/src/main/java/org/rssin/neurons/Neuron.java @@ -8,6 +8,7 @@ import java.util.Random; * Created by Jos on 14-5-2015.
*/
class Neuron {
+ private static final long serialVersionUID = 0;
private static Random r = new Random();
private List<Double> weights = new ArrayList<Double>();
diff --git a/app/src/main/java/org/rssin/neurons/PredictionInterface.java b/app/src/main/java/org/rssin/neurons/PredictionInterface.java index e130f4d..27a214f 100755 --- a/app/src/main/java/org/rssin/neurons/PredictionInterface.java +++ b/app/src/main/java/org/rssin/neurons/PredictionInterface.java @@ -6,4 +6,5 @@ package org.rssin.neurons; interface PredictionInterface {
public double getOutput();
public void learn(double expectedOutput);
+ public double[] getInputs();
}
diff --git a/app/src/main/java/org/rssin/neurons/TrainingCase.java b/app/src/main/java/org/rssin/neurons/TrainingCase.java new file mode 100755 index 0000000..77162be --- /dev/null +++ b/app/src/main/java/org/rssin/neurons/TrainingCase.java @@ -0,0 +1,26 @@ +package org.rssin.neurons;
+
+import java.io.Serializable;
+
+/**
+ * Created by Jos on 20-5-2015.
+ */
+class TrainingCase implements Serializable {
+ private static long serialVersionID;
+ private double[] inputs;
+ private Feedback feedback;
+
+ public TrainingCase(double[] inputs, Feedback feedback)
+ {
+ this.inputs = inputs;
+ this.feedback = feedback;
+ }
+
+ public double[] getInputs() {
+ return inputs;
+ }
+
+ public Feedback getFeedback() {
+ return feedback;
+ }
+}
diff --git a/app/src/main/java/org/rssin/rss/Feed.java b/app/src/main/java/org/rssin/rss/Feed.java index b48f036..3718af2 100644 --- a/app/src/main/java/org/rssin/rss/Feed.java +++ b/app/src/main/java/org/rssin/rss/Feed.java @@ -13,32 +13,54 @@ import java.util.List; public class Feed implements Serializable { private static final long serialVersionUID = 2; - private String guid; - private Date pubDate; - private String title; + private List<String> category = new LinkedList<>(); + private String cloud; + private String copyright; private String description; + private String docs; + private String generator; + private String imageurl; + private String imagetitle; + private String imagelink; + private String language; + private Date lastBuildDate; private String link; - private String author; - private List<String> category = new LinkedList<>(); - private String comments; - private String enclosure; - private String source; + private String managingEditor; + private Date pubDate; + private String rating; + private String skipDays; + private String skipHours; + private String textInput; + private String title; + private String ttl; + private String webMaster; private List<FeedItem> posts = new ArrayList<>(); - public Feed (String guid, Date pubDate, String title, String description, String link, - String author, List<String> category, String comments, String enclosure, String source) - { - this.guid = guid; - this.pubDate = pubDate; - this.title = title; - this.description = description; - this.link = link; - this.author = author; + public Feed(List<String> category, String cloud, String copyright, String generator, + String imageurl, String imagetitle, String imagelink, String language, + Date lastBuildDate, String link, String managingEditor, Date pubDate, + String rating, String skipDays, String skipHours, String textInput, + String title, String ttl, String webMaster) { this.category = category; - this.comments = comments; - this.enclosure = enclosure; - this.source = source; + this.setCloud(cloud); + this.setCopyright(copyright); + this.setGenerator(generator); + this.setImageurl(imageurl); + this.setImagetitle(imagetitle); + this.setImagelink(imagelink); + this.setLanguage(language); + this.setLastBuildDate(lastBuildDate); + this.setLink(link); + this.setManagingEditor(managingEditor); + this.setPubDate(pubDate); + this.setRating(rating); + this.setSkipDays(skipDays); + this.setSkipHours(skipHours); + this.setTextInput(textInput); + this.setTitle(title); + this.setTtl(ttl); + this.setWebMaster(webMaster); } public void addPost(FeedItem post) { @@ -49,42 +71,171 @@ public class Feed implements Serializable { return posts; } - public String getGuid() { - return guid; + public String getCloud() { + return cloud; } - public Date getPubDate() { - return pubDate; + public void setCloud(String cloud) { + this.cloud = cloud; } - public String getTitle() { - return title; + public List<String> getCategory() { + return category; + } + + public void setCategory(String category) { + this.category.add(category); + } + + public String getCopyright() { + return copyright; + } + + public void setCopyright(String copyright) { + this.copyright = copyright; } public String getDescription() { return description; } + public void setDescription(String description) { + this.description = description; + } + + public String getDocs() { + return docs; + } + + public void setDocs(String docs) { + this.docs = docs; + } + + public String getGenerator() { + return generator; + } + + public void setGenerator(String generator) { + this.generator = generator; + } + + public String getImageurl() { + return imageurl; + } + + public void setImageurl(String imageurl) { + this.imageurl = imageurl; + } + + public String getImagetitle() { + return imagetitle; + } + + public void setImagetitle(String imagetitle) { + this.imagetitle = imagetitle; + } + + public String getImagelink() { + return imagelink; + } + + public void setImagelink(String imagelink) { + this.imagelink = imagelink; + } + + public String getLanguage() { + return language; + } + + public void setLanguage(String language) { + this.language = language; + } + + public Date getLastBuildDate() { + return lastBuildDate; + } + + public void setLastBuildDate(Date lastBuildDate) { + this.lastBuildDate = lastBuildDate; + } + public String getLink() { return link; } - public String getAuthor() { - return author; + public void setLink(String link) { + this.link = link; } - public List<String> getCategory() { - return category; + public String getManagingEditor() { + return managingEditor; } - public String getComments() { return comments; } + public void setManagingEditor(String managingEditor) { + this.managingEditor = managingEditor; + } + + public Date getPubDate() { + return pubDate; + } + + public void setPubDate(Date pubDate) { + this.pubDate = pubDate; + } + + public String getRating() { + return rating; + } + + public void setRating(String rating) { + this.rating = rating; + } - public String getEnclosure() { - return enclosure; + public String getSkipDays() { + return skipDays; } - public String getSource() { - return source; + public void setSkipDays(String skipDays) { + this.skipDays = skipDays; } -} + public String getSkipHours() { + return skipHours; + } + + public void setSkipHours(String skipHours) { + this.skipHours = skipHours; + } + + public String getTextInput() { + return textInput; + } + + public void setTextInput(String textInput) { + this.textInput = textInput; + } + + public String getTitle() { + return title; + } + + public void setTitle(String title) { + this.title = title; + } + + public String getTtl() { + return ttl; + } + + public void setTtl(String ttl) { + this.ttl = ttl; + } + + public String getWebMaster() { + return webMaster; + } + + public void setWebMaster(String webMaster) { + this.webMaster = webMaster; + } +}
\ No newline at end of file diff --git a/app/src/main/java/org/rssin/rss/FeedItem.java b/app/src/main/java/org/rssin/rss/FeedItem.java index 1c5348e..bb074cd 100644 --- a/app/src/main/java/org/rssin/rss/FeedItem.java +++ b/app/src/main/java/org/rssin/rss/FeedItem.java @@ -19,6 +19,7 @@ public class FeedItem { private String comments; private String enclosure; private String source; + private boolean isRead; public FeedItem(String guid, Date pubDate, String title, String description, String link, String author, List<String> category, String comments, String enclosure, String source) @@ -122,4 +123,11 @@ public class FeedItem { return title + "\n" + description + " - " + author; } + public boolean isRead() { + return isRead; + } + + public void setIsRead(boolean isRead) { + this.isRead = isRead; + } } diff --git a/app/src/main/java/org/rssin/rss/FeedLoader.java b/app/src/main/java/org/rssin/rss/FeedLoader.java index db0f1db..726cbac 100644 --- a/app/src/main/java/org/rssin/rss/FeedLoader.java +++ b/app/src/main/java/org/rssin/rss/FeedLoader.java @@ -7,6 +7,7 @@ import java.util.Date; import java.util.LinkedList; import org.xmlpull.v1.XmlPullParser; +import org.xmlpull.v1.XmlPullParserException; import org.xmlpull.v1.XmlPullParserFactory; @@ -17,29 +18,47 @@ public class FeedLoader { private Feed feed; - private String urlString = null; + private URL urlString = null; private XmlPullParserFactory xmlFactoryObject; public volatile boolean parsingComplete = true; - public FeedLoader(Feed feed, String url){ - this.setFeed(feed); + private String text; + + public FeedLoader(URL url){ this.urlString = url; } + /** + * parses an XML file and saves all information in the feed. + * @param myParser the parser in question. + */ public void parseXMLAndStoreIt(XmlPullParser myParser) { int event; - String text=null; FeedItem post = null; + boolean chan = true; //as long as the first item hasn't been reached, all + //information is saved in the feed itself, rather than + //in separate items. try { event = myParser.getEventType(); while (event != XmlPullParser.END_DOCUMENT) { - String name=myParser.getName(); + String name = myParser.getName(); switch (event) { case XmlPullParser.START_TAG: - if(name.equals("item")) - { - post = new FeedItem(null, null, null, null, null, - null, new LinkedList<String>(), null, null, null); + switch (name) { + case "item": + post = new FeedItem(null, null, null, null, null, + null, new LinkedList<String>(), null, null, null); + chan = false; //this starts collection information for the + //separate items. + break; + case "image": + imageTagParse(myParser); + case "channel": + feed = new Feed(new LinkedList<String>(), null, null, null, null, + null, null, null, null, null, null, null, null, null, null, + null, null, null, null); + chan = true; + break; } break; case XmlPullParser.TEXT: @@ -47,55 +66,160 @@ public class FeedLoader { break; case XmlPullParser.END_TAG: assert post != null; - if(name.equals("guid")) { - - post.setGuid(text); - } - else if(name.equals("pubDate")) { - post.setPubDate(new Date(text)); - } - else if(name.equals("title")) { - post.setTitle(text); - } - else if(name.equals("description")) { - post.setDescription(text); - } - else if(name.equals("link")) { - post.setLink(text); - } - else if(name.equals("author")) { - post.setAuthor(text); - } - else if(name.equals("category")) { - post.setCategory(text); - } - else if(name.equals("comments")) { - post.setComments(text); - } - else if(name.equals("enclosure")) { - post.setEnclosure(text); - } - else if(name.equals("source")) { - post.setSource(text); - } - else if(name.equals("item")) { - feed.addPost(post); + if (!chan) { //this saves all the item-related information. + switch (name) { + case "guid": + post.setGuid(text); + break; + case "pubDate": + post.setPubDate(new Date(text)); + break; + case "title": + post.setTitle(text); + break; + case "description": + post.setDescription(text); + break; + case "link": + post.setLink(text); + break; + case "author": + post.setAuthor(text); + break; + case "category": + post.setCategory(text); + break; + case "comments": + post.setComments(text); + break; + case "enclosure": + post.setEnclosure(text); + break; + case "source": + post.setSource(text); + break; + case "item": + getFeed().addPost(post); + break; + } + } else { //this saves all the feed-related information. + switch (name) { + case "category": + getFeed().setCategory(text); + break; + case "cloud": + getFeed().setCloud(text); + break; + case "copyright": + getFeed().setCopyright(text); + break; + case "description": + getFeed().setDescription(text); + break; + case "docs": + getFeed().setDocs(text); + break; + case "generator": + getFeed().setGenerator(text); + break; + case "image": + break; + case "language": + getFeed().setLanguage(text); + break; + case "lastBuildDate": + getFeed().setLastBuildDate(new Date(text)); + break; + case "link": + getFeed().setLink(text); + break; + case "managingEditor": + getFeed().setManagingEditor(text); + break; + case "pubDate": + getFeed().setPubDate(new Date(text)); + break; + case "rating": + getFeed().setRating(text); + break; + case "skipDays": + getFeed().setSkipDays(text); + break; + case "skipHours": + getFeed().setSkipHours(text); + break; + case "textInput": + getFeed().setTextInput(text); + break; + case "title": + getFeed().setTitle(text); + break; + case "ttl": + getFeed().setTtl(text); + break; + case "webMaster": + getFeed().setWebMaster(text); + break; + case "item": + getFeed().addPost(post); + break; + } } break; } - event = myParser.next(); - } - parsingComplete = false; - } catch (Exception e) { - e.printStackTrace(); + event = myParser.next(); } + parsingComplete = false; + } catch (Exception e) { + e.printStackTrace(); } + } + + /** + * This function parses the child elements of the <image>tag. + * @param myParser XML parser. + * @throws XmlPullParserException + */ + public void imageTagParse(XmlPullParser myParser) throws XmlPullParserException { + int event; + boolean imageloop = true; + event = myParser.getEventType(); + while (imageloop) { + String name = myParser.getName(); + switch (event) { + case XmlPullParser.START_TAG: + break; + case XmlPullParser.TEXT: + text = myParser.getText(); + break; + case XmlPullParser.END_TAG: + switch (name) { + case "url": + getFeed().setImageurl(text); + break; + case "title": + getFeed().setImagetitle(text); + break; + case "link": + getFeed().setImagelink(text); + break; + case "image": + imageloop = false; + break; + } + } + } + } + + /** + * Retrieves the XML and parses it. + */ public void fetchXML(){ Thread thread = new Thread(new Runnable(){ @Override public void run() { try { - URL url = new URL(urlString); + URL url = urlString; HttpURLConnection conn = (HttpURLConnection) url.openConnection(); conn.setReadTimeout(10000 /* milliseconds */); conn.setConnectTimeout(15000 /* milliseconds */); @@ -120,4 +244,8 @@ public class FeedLoader { public void setFeed(Feed feed) { this.feed = feed; } + + public Feed getFeed() { + return feed; + } } diff --git a/app/src/main/java/org/rssin/rssin/FeedLoaderAndSorter.java b/app/src/main/java/org/rssin/rssin/FeedLoaderAndSorter.java new file mode 100755 index 0000000..eda0526 --- /dev/null +++ b/app/src/main/java/org/rssin/rssin/FeedLoaderAndSorter.java @@ -0,0 +1,64 @@ +package org.rssin.rssin;
+
+import org.rssin.neurons.FeedSorter;
+import org.rssin.rss.FeedItem;
+import org.rssin.rss.FeedLoader;
+
+import java.util.ArrayList;
+import java.util.List;
+
+/**
+ * Created by Jos on 20-5-2015.
+ */
+public class FeedLoaderAndSorter {
+ private Filter filter;
+
+ public FeedLoaderAndSorter(Filter filter) {
+ this.filter = filter;
+ }
+
+ /**
+ * Loads the feed(s), filters it, sorts it, and returns the result.
+ * @return The filtered & sorted list of feedtems.
+ */
+ public List<FeedItem> getFilteredFeedItems()
+ {
+ List<FeedItem> resultingItems = new ArrayList<FeedItem>();
+ for(Feed feed : filter.getFeeds())
+ {
+ FeedLoader loader = new FeedLoader(feed.getURL());
+ loader.fetchXML();
+ org.rssin.rss.Feed loadedFeed = loader.getFeed();
+ for(FeedItem item : loadedFeed.getPosts())
+ {
+ if(matchesKeyword(item))
+ {
+ resultingItems.add(item);
+ }
+ }
+ }
+
+ FeedSorter sorter = filter.getSorter();
+ return sorter.sortItems(resultingItems);
+ }
+
+ private boolean matchesKeyword(FeedItem item)
+ {
+ for(Keyword keyword : filter.getKeywords())
+ {
+ if(contains(item.getTitle(), keyword.getKeyword()))
+ {
+ return true;
+ }
+ }
+
+ return filter.getKeywords().size() == 0;
+ }
+
+ private static boolean contains( String haystack, String needle ) {
+ haystack = haystack == null ? "" : haystack;
+ needle = needle == null ? "" : needle;
+
+ return haystack.toLowerCase().contains(needle.toLowerCase());
+ }
+}
diff --git a/app/src/main/java/org/rssin/rssin/Filter.java b/app/src/main/java/org/rssin/rssin/Filter.java index a5a4cd9..e0e05d0 100644..100755 --- a/app/src/main/java/org/rssin/rssin/Filter.java +++ b/app/src/main/java/org/rssin/rssin/Filter.java @@ -2,6 +2,9 @@ package org.rssin.rssin; import android.text.TextUtils; +import org.rssin.neurons.FeedSorter; +import org.rssin.rss.FeedItem; + import java.io.Serializable; import java.util.ArrayList; import java.util.List; @@ -15,7 +18,8 @@ public class Filter implements Serializable { private final List<Feed> feeds; private final List<Keyword> keywords; - private String title = new String(""); + private String title = ""; + private FeedSorter sorter; public Filter() { feeds = new ArrayList<>(); @@ -65,4 +69,7 @@ public class Filter implements Serializable { this.title = title; } + public FeedSorter getSorter() { + return sorter; + } } |