Calling Java method that uses hash map as a parameter - java

I have a method in an android application:
public void changeImageView (HashMap<String,String> Detail)
I have been trying to call this method in the onCreate method in the same class.
I have tried:
changeImageView();
and
changeImageView(HashMap<String,String> Detail);
Both of which give me errors. The first gives me an error stating that the parameters are missing - understandable. But when I try the second version, I get an error saying "expression expected" with HashMap<String,String>.
I am probably missing something very obvious and have been unable to find anything online that can answer my question.

First, create an instance of HashMap<String, String>.
Map<String, String> map = new HashMap<>();
After its filling or other operations on the map, pass it as a parameter to your method.
changeImageView(map);
I would suggest you reading about methods on Oracle Tutorials.

HashMap is a collection class available in java.util package.
A method changeImageView() here has a definition which takes a HashMap object of type [Generic Type : Google it to know more about it].
You need to create a HashMap object :
Map<String,String> map=new HashMap<String,String>();
You can add values to the above hashmap as given below :
map.add("key1","value1");
map.add("key2","value3");
depending upon your requirements.
Now you can pass this map object to the changeImageView() method as given below:
changeImageView(map)
Seems like you are a newbie to Java and OOP , please refer any Java basic tutorials . This will help you to build up your basic concepts.

Related

How to place a Map into another Map in Java

I'm doing a personal project.
After a lot of maps, I came to the point where I want to enter a map inside another map... Let me explain better.
I have this Map atPropostas which have information about a person, but at some time of the program, I want to add to that person a boss email.
private Map<String, Long> atPropostas;
private Map<String,Map<String,Long>> atOrientadores;
To add that boss email, I've done this:
for (Map.Entry<String, Long> atprop : atPropostas.entrySet()) {
for (Map.Entry<String, Proposta> prop : propostas.entrySet()) {
if (prop.getValue().getTipo().equals("T2") && propostas.containsKey(atprop.getKey())) {
atOrientadores.put(prop.getValue().getEmailDocente(), atprop);
}
}
}
But, atprop value, inside atOrientadores.put() it produces an error:
java: incompatible types:
java.util.Map.Entry<java.lang.String,java.lang.Long> cannot be
converted to java.util.Map<java.lang.String,java.lang.Long>
I have tried to cast the atprop:
atOrientadores.put(prop.getValue().getEmailDocente(), (Map<String, Long>) atprop);
And the compiler error disappears, but the App itself, doesn't working.
You can't convert Map.Entry in to a Map with casting.
Map and entry represent inherently different notions. Map consists of entries, it isn't an entry.
You can create a single entry map by using static method Map.ofEntries() available with Java 9
atOrientadores.put(prop.getValue().getEmailDocente(), Map.ofEntries(atprop));
Sidenote: it's highly advisable to use English while giving names to variables, classes, etc. in your application. It makes it easier to reason about your code.
I don't know for sure what atprop is meant to represent, but you've mentioned a person and an email. I advise you to consider creating classes that would correspond to a person and an email instead of complicating your code and dealing with nested maps.

Mockito anyListOf, anyMapOf, anyCollectionOf deprecated replacement

I am working on a Java 8 to Java 17 update and the project includes a very old version of Mockito.
When I update the library to Mockito 4.4.0 I found out that there many libraries which has been completely removed, most of them are related with validation of objects that you can set the variable type at compilation time, for instance:
If you have the following object:
Map<String,Object> map
Then you can validate with Mokito if the map is of type String, Object by using:
anyMapOf(String.class,Object.class)
The thing in here is that I thought that one of this both could be a good approach:
//Create the map first
Map<String,Object> map = new HashMap<>();
//Then use the method "any" calling the getClass method
any(map.getClass())
But now I'm pretty sure that it is not the same.
On the other hand, I found the following forum:
java generics: getting class of a class with generic parameters
From which I get this code:
(Class<Map<String,Object>>)(Class)Map.class
This also seems to work if you use it with any, like so:
any((Class<Map<String,Object>>)(Class)Map.class)
But obviously, it triggers a warning message and it doesn't seem to be the best solution.
Finally, I read in the Mockito documentation that this clases were only used for generic friendliness to avoid casting before Java 8, so that means that if I use anyMap in Java 8 and upwards it will work the same as anyMapOf?
I have been searching for hours for which could be the best replacement for this deprecated method but I just can't find the right answer.
Try this:
ArgumentMatchers.<String,Object>anyMap()
or this:
Map<String,Object> mapToGoIntoTheMock = anyMap()

Redefine ConstraintViolation from hibernate validator

We are using the java EE 7 with Wildfly 10.0. In the last few days I am learning a lot of Bean validation feature that is included in Java EE 7 specification. It sounds promising, as I see many advantages in using annotations for validations including reusabilty and cleaner code.
However the javax.validation.Validator returns a Set of ConstraintViolations.
Now, the ConstraintViolation has a message attached to it which you can get from it with getMesssage(). The type of the message is a String.
However, for our error handling we use a custom type that we created called a Pair<int, String>, to return message to the client including error code and a message.
Here is an example of how our pairs look like:
public static final Pair<Integer, String> NAME_VALIDATION_ERROR = new Pair<Integer, String>(
201, "Name must contain only letters");
Now, this is all in a class called ErrorStrings and it's easy to use because that class contains static methods and when you start typing ErrorStrings. the autocomplete gives you the names of the error pairs you can use. For example NAME_VALIDATION_ERROR.
So, what would be the easiest way to add Pair<int, String> to the ConstraintViolation, so that it can be used to return the response to the client without adding complexity to the code.
I thougth of adding a Hashmap<String, Pair<int, String>> to the ErrorStrings class, and using a message defined in ConstraintViolation as a key, but that would add much complexity to that class as you would have to change a pair and a hashmap when you would like to change or add some error.
I am using a hibernate validator, which is a default implementation for Jave EE, but I am willing to use any other implementation. I would like to know the easiest way, to redefine ConstraintViolation so it has Pair<int, String> in it.
The "easiest" way I know is that you should create your own custom contraints, which would throw custom ConstraintViolation implementations, which could also have a public Pair<Integer, String> getMessagePair() method. But this would be even more complex, as it would require you to reimplement every single validation you do.
Personally I would do the translation from String to Pair<Integer, String> in a new ErrorStringTranslator class. This is a bit cleaner solution than the one you mentioned, but doesn't save you from the complexity of the task.

Bukkit Config - get Subsections and safe casting

I have the following config file:
arenas
arena1
info: infotest
info2: info2test
arena2
info: infotest
info2: info2test
So. Now i want to get one arena, and convert it to a arena object, i have a constructor there taking a Map. So i do following:
Arena a = new Arena((Map<String, Object>) getConfig().get("arenas.arena1"));
That is working. But: im getting the following warning in eclipse:
Type safety: Unchecked cast from Object to Map<String,Object>
I undestand why this apperas. but how can i change the way getting the informations to avoid this, so to make a "safe" cast?
And my second question: Now i want to get all the sub Map 's from arenas.""
and initialize them when the plugin loads. How can i get all of them? I cannot find something like arenas.getAll() or i dont know.. something like this.. anyone an idea?
Thank you.
For your first question, you can get the configuration section "arena1" and get all of the values as a Map without any warnings. To do this, use:
config.getConfigurationSection("arenas.arena1").getValues(false);
Alternatively, you can just put #SupressWarnings("unchecked") over the method where you're using that code. Since you know the type you're getting will be a Map, the warning doesn't really mean much, though some developers might consider this bad practice.
For your second question, you can use a similar method. getValues() is essentially a getAll() type of method, it gets a map of all of the keys and values in the section. So you could use:
config.getConfigurationSection("arenas").getValues(false);

Passing information between Java LoginModules (Generic Map Problem)

I am currently trying to write some LoginModules to enable users to log into a Java application. Here is my .java.login.config file:
"Java Application" {
path.to.login.module.PamLoginModule sufficient;
path.to.login.module.OtherLoginModule sufficient;
};
So if the PamLoginModule fails, I want to pass information to the OtherLoginModule. This way, the OtherLoginModule doesn't have to ask for the user name and password again. So I am guessing that this is what the sharedState Map is for in the initialize() function:
initialize(Subject subject, CallbackHandler callbackHandler,
Map<String,?> sharedState, Map<String,?> options)
The problem is that you can't put things into the sharedState map. If I do something like:
sharedState.put("key", value); // Value is a string
The compiler complains:
path/to/login/module/PamLoginModule.java:48: put(java.lang.String,capture#833 of ?) in java.util.Map<java.lang.String,capture#833 of ?> cannot be applied to (java.lang.String,java.lang.String)
this.sharedState.put("key", value);
I have found a way to get around this, but I want to know what the correct way is.
First, I can use the java 1.4.2 version of initialize which is:
initialize(Subject subject, CallbackHandler callbackHandler, Map sharedState, Map options)
This way I just receive generic maps and I can just cast the Map object to a Map
Map<String,Object> this.sharedState = (Map<String,Object>)sharedState;
The problem is that I still get unchecked cast exceptions. Now, I know the people who made the LoginModule interface aren't stupid, so I am wondering why they made the sharedState map a Map<String,?> as opposed to a Map<String,Object>. Also, is there a better way to put things into the sharedState map?
Thanks!
If you look at the LoginModule implementations in the Java SDK, they save those maps into local fields without the generics info, that is plain Maps. And in the code they do put objects there (at least when the user is authenticated). So the use of the question mark in the LoginModule interface has to be a design mistake.
I am wondering why they made the
sharedState map a Map<String,?> as
opposed to a Map<String,Object>.
This is exactly what I'm wondering.
I guess the purpose of using ? is to accept anything (I don't really see another explanation), so using Object would be completely right and standard.
If you're posting here I guess you cannot ask who coded it this way (using ?) to know why.
Therefore you should investigate a bit the related classes/methods to discover if there is really a meaningful and specific use for ?. Otherwise you should make it a <String, Object>.
I've personnally never seen that current use, except when ? is specified as <? implements MyInterface> or <T extends MySuperClass> for example. In the first case, you should be able to do Map<String, MyInterface> anyway with the same result.
Sorry if I don't have a specific answer but I hope this helps you!

Categories

Resources