How to split following string in java using brace - java

{"smscresponse":{"calluid":"3333","to":"0000","event":"ABC"}}
I am using
split("{")[1] to get "calluid":"3333","to":"0000","event":"ABC"
But i am getting
Illegal repetition
{ error.
What i want is calluid .How i can get that one.
Thanks in advance...

You could escape the { character, something like...
String text = "{\"smscresponse\":
{\"calluid\":\"3333\",\"to\":\"0000\",\"event\":\"ABC\"}}";
String[] split = text.split("\\{");
System.out.println(split.length);
System.out.println(split[2]);
Which outputs...
3
"calluid":"3333","to":"0000","event":"ABC"}}
To get "3333", you could do something like...
split = split[2].split(":|,"); // Split on : or ,
System.out.println(split[1]);
Which outputs
"3333"
Now, if you really wanted to be clever, you could try something like...
String[] split = text.split("\\{|:|,|\\}");
for (String part : split) {
System.out.println(part);
}
Which outputs
// Note, this is an empty line
"smscresponse"
// Note, this is an empty line
"calluid"
"3333"
"to"
"0000"
"event"
"ABC"
Updated...
A slightly better solution might be...
Pattern p = Pattern.compile("\"([^\"]*)\"");
Matcher m = p.matcher(text);
while (m.find()) {
System.out.println(m.group());
}
Which outputs
"smscresponse"
"calluid"
"3333"
"to"
"0000"
"event"
"ABC"

Try to split using input.split("[{]");
String abc = "{\"smscresponse\":{\"calluid\":\"3333\",\"to\":\"0000\",\"event\":\"ABC\"}}";
String[] splittedValue = abc.split("[{]");
for(String value : splittedValue)
System.out.println(""+value);

String s = "{\"smscresponse\":{\"calluid\":\"3333\",\"to\":\"0000\",\"event\":\"ABC\"}}";
System.out.println(s.split("\\{")[2].split("}")[0]);
Don't worry about "\". This will work for your dynamically generated data.
EDIT : This will get you "calluid"
System.out.println(s.split("\\{")[2].split("}")[0].split(",")[0]);

Create a JSON object of the given string and parse the JSON object to fetch the value. Use the library org.json
import java.io.FileNotFoundException;
import java.io.FileReader;
import java.io.IOException;
import java.util.Iterator;
import org.json.simple.JSONArray;
import org.json.simple.JSONObject;
import org.json.simple.parser.JSONParser;
import org.json.simple.parser.ParseException;
public class JsonSimpleExample {
public static void main(String[] args) {
JSONParser parser = new JSONParser();
try {
JSONObject jsonObj = new JSONObject("{\"smscresponse\":{\"calluid\":\"3333\",\"to\":\"0000\",\"event\":\"ABC\"}}");
String calluid = (String) jsonObject.get("smscresponse").getString("calluid");
System.out.println(calluid);
} catch (ParseException e) {
e.printStackTrace();
}
}
}

Related

How to create JSON in java for pipe delimiter?

Suppose i have this structure
FirstName| Auro
LastName|Winkies
Age|26
How can we convert it into json I want the word which are before pipe delimiter | should be in L property and the word which are after pipe delimiter | should be shuffled and saved it into another property R and the C property is like Winkies is at 2 position after pipe delimiter , similarly auro is at 1 position and 26 is at 3 position
Is it possible to create this json structure in java.
I thought first i need to split \n and further split it into \\|
{
"L": ["FirstName" , "LastName" , "Age"],
"R": ["Winkies" , "Auro" , "26"],
"C":["2" ,"1" , "3"]
}
If possible anybody can help me out with the logic
i don't find the utility of the "C" field but here is solution
import com.fasterxml.jackson.databind.node.JsonNodeFactory;
import com.fasterxml.jackson.databind.node.ObjectNode;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;
public static void main(final String[] args) {
String data = "FirstName|Auro\n" +
"LastName|Winkies\n" +
"Age|26";
List<String> l = new ArrayList<>();
List<String> r = new ArrayList<>();
ObjectNode node = JsonNodeFactory.instance.objectNode();
List<String> c = Arrays.asList("1,2,3");
String[] split = data.split("\n");
for (String s : split) {
int i = s.indexOf('|');
l.add(s.substring(0, i));
r.add(s.substring(i + 1, s.length()));
}
node.put("L",l.toString());
node.put("R",r.toString());
node.put("C",c.toString());
System.out.println(node);
}

How to remove null keys from JSON Object

I have the below JSON , i need to remove all the keys which have null value
I have tried this
import java.util.Iterator;
import org.json.JSONException;
import org.json.JSONObject;
public class Remove {
public static void main(String[] args) throws JSONException {
String str = "{\r\n" +
" \"videos\": {\r\n" +
"
" }}";
JSONObject json_obj = new JSONObject(str);
JSONObject allKeys_json= json_obj.getJSONObject("videos");
Iterator<String> keys = allKeys_json.keys();
while( keys.hasNext() ) {
String keyanme = (String)keys.next();
String keyvalue = allKeys_json.getString(keyanme);
if(keyvalue.contains("null"))
{
System.out.println(keyanme+"\t"+keyvalue);
json_obj.remove(keyanme);
}
}
System.out.println(allKeys_json);
}
}
but the actual json is unaffected , could you please tell me how to do this .
If it's only about manipulating a string which structure you know well a solution would be to use some regex
str.replaceAll(".*\": null(,)?\\r\\n", "");
It could be easier to find a good regex than to invest time in building a model that could be used by Jackson.
Three notes:
the code above doesn't figure out which is the last line and adapt the json accordingly.
the pattern should be compiled separately.
org.json is very inefficient compared to Jackson.
Check your null value like this
if(keyvalue == null)
This fixex the issue
Firstly, create an model class which is corresponding to the JSON string.
Add
#JsonIgnoreProperties(ignoreUnknown = true)
to your model class such as
#JsonIgnoreProperties(ignoreUnknown = true)
public class Video {
//the properties
}
http://www.baeldung.com/jackson-deserialize-json-unknown-properties
Use Jackson API and use #JsonInclude(Include.NON_NULL) on your model/DTO class to remove.
Like
#JsonInclude(Include.NON_NULL)
#JsonIgnoreProperties(ignoreUnknown=true)
public class Video {
//the properties
}
I used it like this and it worked for me.
#JsonInclude(value = Include.NON_NULL)

How to parse a sequence of commands line in the same way bash would?

Input
I have the following example input (each of those is a bash executable command):
client-properties create mode "publisher" "version" "mode"
client-properties set "publisher" "version" "mode" "prop1" "value
value
value"
client-properties set "publisher" "version" "mo\"de" "prop2" "שלום עליכם"
Output
From that, I want to parse it into 3 String[]s as follows:
{"client-properties", "create", "mode", "publisher", "version", "mode"}
{"client-properties", "set", "publisher", "version", "mode", "prop1", "value\nvalue\nvalue"}
{"client-properties", "set", "publisher", "version", "mo\"de", "prop2", "שלום עליכם"}
// (mo"de)
Requirements
The hard requirements are as follows:
Newlines denote new statements.
Spaces denote single arguments.
Arguments delimited by double quotes (") are considered a single argument even if it has spaces or newlines
The \" escape sequence may be used to insert a literal double quote in an argument
Unicode characters are allowed (assuming UTF8 is safe).
What I've tried
I've looked into regular expressions, but it got very complicated, very fast. I've looked into StringTokenizer (Which appears very primitive) and StreamTokenizer (Which doesn't handle unicode very well).
I would like to avoid writing a parser by hand if possible.
Any ideas with regards to this? My latest attempt is as follows:
public static List<String> tokenize(String s) {
List<String> opts = new ArrayList<>();
try (StringReader sr = new StringReader(s)) {
StreamTokenizer st = new StreamTokenizer(sr);
st.resetSyntax();
// From ! to end of ascii range. But alas, no unicode
st.wordChars(31, 127);
st.quoteChar('\"');
st.whitespaceChars(32, 32);
while (st.nextToken() != StreamTokenizer.TT_EOF) {
opts.add(st.sval);
}
} catch (IOException e) {}
return opts;
}
You can try with opencsv library, imported using gradle like:
compile 'net.sf.opencsv:opencsv:3.4'
Try something similar to following program:
import com.opencsv.CSVReader;
import java.io.FileNotFoundException;
import java.io.FileReader;
import java.io.IOException;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;
public class Main {
private static final char SEPARATOR = ' ';
private static final char QUOTE_CHAR = '"';
private static final char ESCAPE = '\\';
public static void main(String[] args) throws IOException {
List<String[]> result = new ArrayList<>();
CSVReader reader = new CSVReader(
new FileReader(args[0]),
SEPARATOR,
QUOTE_CHAR,
ESCAPE);
result.addAll(reader.readAll());
for (int i = 0; i < result.size(); i++) {
System.out.println(Arrays.toString(result.get(i)));
}
}
}
That yields:
[client-properties, create, mode, publisher, version, mode]
[client-properties, set, publisher, version, mode, prop1, value
value
value]
[client-properties, set, publisher, version, mo"de, prop2, שלום עליכם]

Java - HTML code: extract part of the tag

I have to extract some integers from a tag of a html code.
For example if I have:
< tag blabla="title"><a href="/test/tt123> TEST 1 < tag >
I did that removing all the chars and leaving only the digits and it worked until in the title name there was another digit, so i got "1231".
str.replaceAll("[^\\d.]", "");
How can I do to extract only the "123" integer?? Thanks for your help!
Jsoup is a good api to play around with html. Using that you could do like
String html = "<tag blabla=\"title\"><a href=\"/test/tt123\"> TEST 1 <tag>";
Document doc = Jsoup.parseBodyFragment(html);
String value = doc.select("a").get(0).attr("href").replaceAll("[^\\d.]", "");
System.out.println(value);
You could do this (a method that removes all duplicates in any number):
int[] foo = new int[str.length];
for(int i = 0; i < str.length; i++) {
foo[i] = Integer.parseInt(str.charAt(i));
}
Set<Integer> set = new HashSet<Integer>();
for(int i = 0; i < foo.length; i++){
set.add(foo[i]);
}
Now you have a set where all duplicate numbers from any string are removed. I saw your last comment not. So this answer might not be very useful to you. What you could do is that the three first digits in the foo array as well, which will give you 123.
First use XPath to parse out only the href value, then apply your replaceAll to achieve what you desired.
And you don't have to download any additional frameworks or libraries for this to work.
Here's a quick demo class on how this works:
package com.example.test;
import java.io.StringReader;
import javax.xml.xpath.XPath;
import javax.xml.xpath.XPathConstants;
import javax.xml.xpath.XPathExpressionException;
import javax.xml.xpath.XPathFactory;
import org.xml.sax.InputSource;
public class Test {
public static void main(String[]args){
String xml = "<tag blabla=\"title\"> TEST 1 </tag>";
XPath xPath = XPathFactory.newInstance().newXPath();
InputSource source = new InputSource(new StringReader(xml));
String hrefValue = null;
try {
hrefValue = (String) xPath.evaluate("//#href", source, XPathConstants.STRING);
} catch (XPathExpressionException e) {
e.printStackTrace();
}
String numbers = hrefValue.replaceAll("[^\\d.]", "");
System.out.println(numbers);
}
}

Null value with get method of hashtable

I have written the following Java program.this program splits the given sentence and tags each word with its parts of speech using standard pos tagger.I have hashed each parts of speech tag with a number in a hash set pos_tag_numb.
I got the correct parts of speech for each word,however when i am tring to get tag number from the hash table ,i get a null value.
import java.util.StringTokenizer;
import java.io.BufferedReader;
import java.io.FileReader;
import java.io.IOException;
import java.util.HashMap;
import java.util.Hashtable;
import java.util.Map;
import edu.stanford.nlp.ling.Sentence;
import edu.stanford.nlp.ling.TaggedWord;
import edu.stanford.nlp.ling.HasWord;
import edu.stanford.nlp.tagger.maxent.MaxentTagger;
class maindemo
{
public static void main(String [] args) throws IOException {
//if(args.length<1) {
//System.err.println("Usage: java SentiWordNetDemoCode <pathToSentiWordNetFile>");
//return;
//}
String pathToSWN = "D:\\Acad !!\\Project_idrbt\\home\\swn\\www\\admin\\dump\\SentiWordNet_3.0.0_20130122.txt";
MaxentTagger tagger = new MaxentTagger("D:\\Acad !!\\Project_idrbt\\stanford-postagger-2014-01-04\\models\\english-left3words-distsim.tagger");
//hashing each pos tag to a number
Hashtable<String,Integer> pos_tag_numb = new Hashtable<String,Integer>();
pos_tag_numb.put("JJ",2);
pos_tag_numb.put("JJR",2);
pos_tag_numb.put("JJS",2);
pos_tag_numb.put("RB",5);
pos_tag_numb.put("RBR",5);
pos_tag_numb.put("RBS",5);
pos_tag_numb.put("WRB",5);
SentiWordNetDemoCode sentiwordnet = new SentiWordNetDemoCode(pathToSWN);
String review="very good little bad";
String[] tokens=review.split(" ");
int ti=0;
for(String s: tokens)
{
String taggedstring=tagger.tagString(s);
String[] word_pos_pair=taggedstring.split("_");
String pos=new String(word_pos_pair[1]);
System.out.println(word_pos_pair[0]+" "+ pos_tag_numb.get( pos ) );
}
}
}
tagger.tagString(s) gives an output of for WORD_POSTAG,Eg: very_RB ,good_JJ
If i add the line System.out.println("tag is "+pos); at line 54 output is
tag is RB
very null
tag is JJ
good null
tag is RB
little null
tag is JJ
bad null
FInally i solved my own problem,i guess the method tagger.tagString() is returning a string with some trailing spaces..i just added one statement
taggedstring= taggedstring.trim();
before i split the string i.e before the statement
String[] word_pos_pair=taggedstring.split("_");

Categories