I want my request parameter map in my custom map like
Map<String, String> reqMap =(HashMap<String, String>)request.getParameterMap();
Above statement gives me following exception
java.lang.ClassCastException: java.util.Collections$UnmodifiableMap
Can any one guide me how can I get all request parameters in my custom map?
Don't want to write for loop to get parameters one by one which cause me performance issue.
Beware of casting the Map to String, String as request.getParameterMap() returns a Map of type String, String[] since Java 6.
http://docs.oracle.com/javaee/6/api/javax/servlet/ServletRequest.html#getParameterMap()
Map<String, String> reqMap = request.getParameterMap();
CustomMap<String, String> customMap = new CustomMap<String,String>();
customMap.putAll(reqMap);
Of course, you may need to iterate through the map elements in your putAll() implementation. Otherwise it is not possible.
UPDATE:
Just saw your comment, Thai is easy then,
Map<String, String> reqMap = request.getParameterMap();
Map<String, String> newMap= new HashMap<String,String>();
newMap.putAll(reqMap);
or, you can even pass the reqMap as a constructor argument to new HashMap<String, String>(reqMap);
You can try this method:
public LinkedHashMap<String, String> returnMapOfRequest(HttpServletRequest request)
{
LinkedHashMap<String, String> map = new LinkedHashMap<String, String>();
try
{
Enumeration<String> parameterNames = request.getParameterNames();
Enumeration<String> headerNames = request.getHeaderNames();
while(headerNames.hasMoreElements())
{
String headerName = headerNames.nextElement();
Enumeration<String> headers = request.getHeaders(headerName);
while(headers.hasMoreElements())
{
String headerValue = headers.nextElement();
map.put(headerName, headerValue);
}
}
HttpSession session = request.getSession();
Enumeration e = session.getAttributeNames();
while(e.hasMoreElements())
{
String key = (String) e.nextElement();
map.put(key, session.getAttribute(key));
}
while(parameterNames.hasMoreElements())
{
String paramName = parameterNames.nextElement();
String[] paramValues = request.getParameterValues(paramName);
for(int i = 0; i < paramValues.length; i++)
{
String paramValue = paramValues[i];
map.put(paramName, paramValue);
}
}
}
catch(Exception e)
{
logger.error("Exception in returnMapOfRequest :: ", e);
}
return map;
}
Change:
Map<String, String> reqMap =(HashMap<String, String>)request.getParameterMap();
To:
Map<String, String> reqMap =(Map<String, String>)request.getParameterMap();
Related
I have an object with structure
List<Map<String(k1), Map<String(k2), String(v2)>>>
I need to convert the above list to
List<Map<String(k2), Map<String(k1), String(v2)>>>
I am stuck on how do i get the nested map using construct like
serviceResults.stream().map((k, v) -> ????)
that will allow me to swap the keys. Is it possible to do it in a way without using loops using Java 8 streams?
Additional Info
This is the code that uses loop construct
List<Map<String, Map<String, String>>> serviceResults = new ArrayList<>();
//Populate the above list
Map<String, Map<String, String>> swpMapOuter = new HashMap<>();
Map<String, String> swpMapInner = new HashMap<>();
for (Map<String, Map<String, String>> stringMapMap : serviceResults) {
for (Map.Entry<String, Map<String, String>> s : stringMapMap.entrySet()) {
String key1 = s.getKey();
Map<String, String> value1 = s.getValue();
for (Map.Entry<String, String> s1 : value1.entrySet()) {
String key2 = s1.getKey();
String value2 = s1.getValue();
swpMapInner.put(key1, value2);
swpMapOuter.put(key2, swpMapInner);
}
}
}
System.out.println("swpMapOuter " + swpMapOuter);
Below is the code with forEach, instead of for loops, but was wondering, if it could be implemented using Stream constructs
Map<String, Map<String, String>> swpMapOuter2 = new HashMap<>();
Map<String, String> swpMapInner2 = new HashMap<>();
serviceResults.forEach((stringMapMap) -> {
stringMapMap.entrySet().forEach((s) -> {
String key1 = s.getKey();
Map<String, String> value1 = s.getValue();
value1.entrySet().forEach((s1) -> {
String key2 = s1.getKey();
String value2 = s1.getValue();
swpMapInner2.put(key1, value2);
swpMapOuter2.put(key2, swpMapInner2);
});
});
});
System.out.println("swpMapOuter2 " + swpMapOuter2);
I have a list of Maps as below:
List<Map<String,Object>> someObjectsList = new ArrayList<Map<String,Object>>();
I am storing the following data in each HashMap
key value
2017-07-21 2017-07-21-07.33.28.429340
2017-07-24 2017-07-24-01.23.33.591340
2017-07-24 2017-07-24-01.23.33.492340
2017-07-21 2017-07-21-07.33.28.429540
I want to iterate through the list of HashMaps and check if the key matches with the first 10 characters of any of the HashMap value, then I want to store those keys and values in the following format. i.e. by using the telemeter 'comma'. The ultimate aim is to group the unique keys of the HashMaps and their relative values (if the key matches with the first 10 characters of any of the HashMap value) in a new HashMap.
key value
2017-07-21 2017-07-21-07.33.28.429340,2017-07-21-07.33.28.429540
2017-07-24 2017-07-24-01.23.33.591340,2017-07-24-01.23.33.492340
I am trying with following java code using StringJoiner, but not getting the results as expected. Any clue on how to frame the logic here?
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.StringJoiner;
public class SampleOne {
public static void main(String[] args) {
// TODO Auto-generated method stub
List<Map<String, Object>> someObjectsList = new ArrayList<Map<String, Object>>();
Map<String, Object> mapOne = new HashMap<String, Object>();
mapOne.put("2017-07-21", "2017-07-21-07.33.28.429340");
Map<String, Object> mapTwo = new HashMap<String, Object>();
mapTwo.put("2017-07-24", "2017-07-24-01.23.33.591340");
Map<String, Object> mapThree = new HashMap<String, Object>();
mapThree.put("2017-07-24", "2017-07-24-01.23.33.492340");
Map<String, Object> mapFour = new HashMap<String, Object>();
mapFour.put("2017-07-21", "2017-07-21-07.33.28.429540");
someObjectsList.add(mapOne);
someObjectsList.add(mapTwo);
someObjectsList.add(mapThree);
someObjectsList.add(mapFour);
for (Map map : someObjectsList) {
StringJoiner sj = new StringJoiner(",");
for (Object key : map.keySet()) {
String value = ((String) map.get(key));
String date = value.substring(0, Math.min(value.length(), 10));
//System.out.println(str);
//System.out.println(value);
if(key.equals(date)) {
sj.add(value);
System.out.println(sj.toString());
}
}
}
}
}
output:
2017-07-21-07.33.28.429340
2017-07-24-01.23.33.591340
2017-07-24-01.23.33.492340
2017-07-21-07.33.28.429540
Make use of the .merge function:
Map<String, Object> finalMap = new HashMap<String, Object>();
for (Map map : someObjectsList) {
for (Object key : map.keySet()) {
String value = ((String) map.get(key));
finalMap.merge((String) key, value, (k, v) -> k + "," + v);
}
}
which outputs:
{2017-07-21=2017-07-21-07.33.28.429340,2017-07-21-07.33.28.429540,
2017-07-24=2017-07-24-01.23.33.591340,2017-07-24-01.23.33.492340}
The same can be achieved by the following one-liner:
someObjectsList.stream()
.flatMap(i -> i.entrySet().stream())
.collect(Collectors.toMap(Entry::getKey, Entry::getValue,
(k, v) -> k + "," + v));
On your code, you are using different StringJoiner on each map. So, it's creating a new instance of it.
You can save your keys on a map. An example code:
(Edit: I did not remove your StringJoiner part.)
public static void main(String[] args) {
// TODO Auto-generated method stub
List<Map<String, Object>> someObjectsList = new ArrayList<Map<String, Object>>();
Map<String, Object> mapOne = new HashMap<String, Object>();
mapOne.put("2017-07-21", "2017-07-21-07.33.28.429340");
Map<String, Object> mapTwo = new HashMap<String, Object>();
mapTwo.put("2017-07-24", "2017-07-24-01.23.33.591340");
Map<String, Object> mapThree = new HashMap<String, Object>();
mapThree.put("2017-07-24", "2017-07-24-01.23.33.492340");
Map<String, Object> mapFour = new HashMap<String, Object>();
mapFour.put("2017-07-21", "2017-07-21-07.33.28.429540");
someObjectsList.add(mapOne);
someObjectsList.add(mapTwo);
someObjectsList.add(mapThree);
someObjectsList.add(mapFour);
Map<String, Object> outputMap = new HashMap<String, Object>();
for (Map map : someObjectsList) {
StringJoiner sj = new StringJoiner(",");
for (Object key : map.keySet()) {
String value = ((String) map.get(key));
String date = value.substring(0, Math.min(value.length(), 10));
//System.out.println(str);
//System.out.println(value);
if(key.equals(date)) {
sj.add(value);
System.out.println(sj.toString());
if(outputMap.containsKey(key)) {
String str = (String) map.get(key);
str = str + "," + value;
outputMap.put((String)key, str);
} else {
outputMap.put((String)key, value);
}
}
}
}
for (String map : outputMap.keySet()) {
System.out.println(map + " " + outputMap.get(map));
}
}
You are looking for the grouping behavior of processing a List. You can use the advantage of java-stream since java-8. In any case, you need a new Map to store the values in order to print them. :
someObjectsList.stream()
.flatMap(i -> i.entrySet().stream()) // flatmapping to entries
.collect(Collectors.groupingBy(Entry::getKey)) // grouping them using the key
In case you want to use for-loops. In this case it is harder since the more entries might appear in each List item:
final Map<String, List<Object>> map = new HashMap<>();
for (Map<String, Object> m: someObjectsList) { // iterate List<Map>
for (Entry<String, Object> entry: m.entrySet()) { // iterate entries of each Map
List<Object> list;
final String key = entry.getKey(); // key of the entry
final Object value = entry.getValue(); // value of the entry
if (map.containsKey(key)) { // if the key exists
list = map.get(key); // ... use it
} else {
list = new ArrayList<>(); // ... or else create a new one
}
list.add(value); // add the new value
map.put(key, list); // and add/update the entry
}
}
Printing out of Map<String, List<Object>> map in both cased will produce the following output:
2017-07-21=[2017-07-21-07.33.28.429340, 2017-07-21-07.33.28.429540],
2017-07-24=[2017-07-24-01.23.33.591340, 2017-07-24-01.23.33.492340]
Any reason you're using Object over String and avoiding safety checks? That said, it's not "the first 10 characters", you want to see if value starts with key full-stop (all your keys are 10 characters). So in that case you can just do if (value.startsWith(key)) { ... }. Don't forget your newlines if the stringjoiner wasn't full. Lastly, you don't need a List, a Map can hold multiple keys at once. An alternative way of doing it:
//LinkedHashMap will preserve our insertion order
Map<String, String> map = new LinkedHashMap<>();
map.put("2017-07-21", "2017-07-21-07.33.28.429340");
map.put("2017-07-24", "2017-07-24-01.23.33.591340");
//note duplicates are overwritten, but no value change here
map.put("2017-07-24", "2017-07-24-01.23.33.492340");
map.put("2017-07-21", "2017-07-21-07.33.28.429540");
// You can also use Java 8 streams for the concatenation
// but I left it simple
List<String> matches = map.entrySet()
.filter(e -> e.getValue().startsWith(e.getKey())
.collect(Collectors.toList());
String concatenated = String.join("\n", matches);
If you wanted to generate that string without streams, it would look like this (again, not using #entrySet for simplicity, but it would be more efficient here):
List<String> matches = new ArrayList<>();
StringJoiner joiner = new StringJoiner("\n");
for (String key : map.keySet()) {
String value = map.get(key);
if (value.startsWith(key)) {
joiner.add(value);
}
}
//joiner#toString will give the expected result
I am trying to set a hashmap to have key as string and a list array as value. Is it possible? and how do I set the list into the value?
HashMap<String, List<String>> foo = new HashMap<String, List<String>>();
foo.put("key1",{"key1_value1","key1_value2"});
You can do the following
Map<String, List<String>> foo = new HashMap<String, List<String>>();
List<String> list = new ArrayList<String>();
list.add("key1_value1");
list.add("key1_value2");
foo.put("key1",list);
foo.put("key", Arrays.asList("key1_val1", "key1_val2"));
You have to use a data structure like ArrayList or just an array maybe to represent the list of strings as value.
You can use the following with a List;
foo.put("key", Arrays.asList("key1_val1", "key1_val2"));
where foo is of type Map<String, List<String>>
Or you the following with an array;
foo.put("key", new String[]{"key1_val1", "key1_val2"});
where foo is of type Map<String, String[]>
Map<String, List<String>> foo = new HashMap<String, List<String>>();
List<String> list = new ArrayList<String>();
list.add("value1");
list.add("value2");
foo.put("key1", list);
for (Entry<String, List<String>> entry : foo.entrySet()) {
String key = entry.getKey();
List<String> valueList = entry.getValue();
System.out.println("key = " + key);
for (String value : valueList) {
System.out.println("value = " + value);
}
}
Output
key = key1
value = value1
value = value2
I want to search data from a table where Map<String,String> is passed as parameter in search method. It will also return a Map<String,String>.
I want to solve it using Spring and Hibernate.e.g:
Map<String, String> findByItem(Map<String, String> q){
}
if you can not change method signature. i think it will be below...
Map<String, String> findByItem(Map<String, String> q){
Query listQuery = session.createSQLQuery("SELECT quiestionnaireCode, questionnaireName FROM Questionnaire WHERE quiestionnaireCode =:quiestionnaireCode AND quiestionnaireName =:quiestionnaireName");
listQuery.setParameter("quiestionnaireCode", q.get("quiestionnaireCode");
listQuery.setParameter("quiestionnaireName", q.get("quiestionnaireName");
List<Questionnaire> quiestionnaireList= listQuery.list();
Gson gson = new Gson();
String str = gson.toJson(quiestionnaireList);
Map<String, String> output = new HashMap<String, String>();
output.add("result",str);
return output;
}
I have string variable String temp="acc=101&name=test"; and now how to get the value of name param from temp string.
temp.split("&")[1].split("=")[1]
public static Map<String, String> getParamMap(String query)
{
String[] params = query.split("&");
Map<String, String> map = new HashMap<String, String>();
for (String param : params)
{
String name = param.split("=")[0];
String value = param.split("=")[1];
map.put(name, value);
}
return map;
}
String temp="acc=101&name=test";
Map<String, String> map = getParamMap(temp);
for(Object object :map.keySet()){
System.out.println("key= "+object +" value= "+map.get(object));
}
System.out.println(map.get("name"));
Here is a non-general way
String str = "name=";
System.out.println(temp.substring(temp.indexOf(str) + str.length()));
It could be implemented in more general way of course:
String temp = "acc=101&name=test";
StringTokenizer st = new StringTokenizer(temp, "&");
String paramName = "name";
String paramValue = "";
while(st.hasMoreElements()) {
String str = st.nextToken();
if (str.contains(paramName)) {
paramValue = str.substring(str.indexOf(paramName) + paramName.length() + 1);
break;
}
}
System.out.println(paramValue);
You can use a method like below
public static String getValue(String queyStr, String paraamName){
String[] queries=queyStr.split("&");
for(String param:queries){
if(param.indexOf(paraamName)!=-1)
return param.split("=")[1];
}
return null;
}
And call the method like
getValue(temp, "name")
public static void main(String[] args)
{
String temp = "acc=101&name=test";
System.out.println(temp.split("&")[1].split("=")[1]);
}
If you are looking for a way to parse GET-Parameters out of an URL:
public static Map<String, String> splitQuery(URL url) throws UnsupportedEncodingException {
Map<String, String> query_pairs = new LinkedHashMap<String, String>();
String query = url.getQuery();
String[] pairs = query.split("&");
for (String pair : pairs) {
int idx = pair.indexOf("=");
query_pairs.put(URLDecoder.decode(pair.substring(0, idx), "UTF-8"), URLDecoder.decode(pair.substring(idx + 1), "UTF-8"));
}
return query_pairs;
}
You can access the returned Map using <map>.get("name"), with the URL given in your question this would return "test".
Assuming you have constant format :
String temp="acc=101&name=test";
String result =temp.substring(temp.lastIndexOf("=")+1,temp.length());
//result is test
String temp="acc=101&name=test";
String[] split = temp.split("&");
String[] name = split[1].split("=");
System.out.println(name[1]);
I would put the whole parameter in a HashMap so it is easy to get the values.
HashMap<String, String> valuemap = new HashMap<String, String>();
If you do it like so, you have to split the values at the right place...
String temp="acc=101&name=test";
valuemap.put(temp.split("&")[0].split("=")[0], temp.split("&")[0].split("=")[1]);
valuemap.put(temp.split("&")[1].split("=")[0], temp.split("&")[1].split("=")[1]);
...and put them into your HashMap. Than you have a nice collection of all your values and it is also better if you have more than only that two values. If you want the value back, use:
valuemap.get("acc")
valuemap.get("name")