in my class extend ConstraintLayout. I have defined val-type variables in the class.
After running the program in the debug mode, I see that all the variables are zero.
Why is this going to happen?
When you define variables with initializers, the Kotlin compiler will generate a constructor which will execute all the initializers in sequence. Before the initializers are executed, the values of the corresponding fields will be 0, and this is the state that is shown on your screenshot.
For values such as IMEOPTIONS_ACTION_DONE, which seem to be constants, you shouldn't use regular class properties. Instead, you should put them into a companion object or on the top level of a file.
Related
The following code shows up "Property must be initialized or be abstract" error.I understand that I can use lateinit in such cases but I wanted to know the reason behind the restriction .
class Student{
val s:String
}
In the case of a non-nullable property like in your example, the reason is necessity. Java implicitly gives member variables a value of null. In Kotlin, a non-nullable property cannot have a value of null, so you have to give it an instance of something to be the starting value.
But even if you declared it as nullable String?, Kotlin will require you to specify the starting value. Kotlin avoids making implicit assumptions about the intent of your code. Kotlin's design goals are to make code more readable and robust. The designers have done research on common causes of bugs in other languages, and have made Kotlin more restrictive in areas that have been frequent sources.
I'm using Kotlin for development. When I reached the official Android tutorial's fragment section, I came across the supportFragmentManager. Which is available to use as a variable in Kotlin, whereas in java we can call its equivalent method getSupportFragmentManager().
I wonder where is the supportFragmentManager variable defined as I could not see anything like a variable declaration with that name, however clicking that variable took me to the following method inside fragmentActivity.java class.
/**
* Return the FragmentManager for interacting with fragments associated
* with this activity.
*/
public FragmentManager getSupportFragmentManager() {
return mFragments.getSupportFragmentManager();
}
How does this method come to be accessible as a variable in Kotlin whereas in java we've to access like a regular method? Any help would be appreciated.
Actually, in Kotlin when you call supportFragmentManager it's not variable, Any Java method contains get prefix (without argument) in the method in Kotlin it will be called like a variable without get word
Methods that follow the Java conventions for getters and setters (no-argument methods with names starting with get and single-argument methods with names starting with set) are represented as properties in Kotlin. Boolean accessor methods (where the name of the getter starts with is and the name of the setter starts with set) are represented as properties which have the same name as the getter method.
Read more about here
This is something like the getter and setter method in Kotlin. You don't need to describe getProperty() and setProperty() method to access/update value of property.
You can know more about how it actually works with an example from this question/answers.
I hope it will help you.
Happy coding..!
In kotlin, if we use a when block on an enum while exhausting all the enum values but without adding an else branch, we get this warning: "Enum argument can be null in Java, but exhaustive when contains no null branch".
Android Studio then suggest to add the suppress flag #Suppress("WHEN_ENUM_CAN_BE_NULL_IN_JAVA") either to the statement, function, class or file scope.
Is there any way to add this to the project scope ? Since my project is 100% Kotlin I don't need this warning and would like to disable it globally.
I am trying to make sense of a class from a library. The class has no constructor, and I think it is being instantiated via reflection. It is a confusing library, and I want to figure out what is creating instances of this class... but I cannot figure out where to put a breakpoint, since there is no constructor.
I have tried the following, and Android Studio 3.4.1 blows right past them:
Line breakpoints on fields in the class that have initializers
Field watchpoints, set for both field access and field modification, for fields that have initializers
A breakpoint on the class declaration (class Foo)
Breakpoints in methods work, and field watchpoints work when the field is accessed later on (but not when it is initialized). So the debugger is working with this class in general.
I cannot readily recompile the library to add a constructor, though I do have source code (not just decompiled bytecode).
Is there another spot that I can put a breakpoint that will show me the stack trace of instantiation of this class?
From the InitelliJ IDEA documentation (on which AS is based):
If you want to set a breakpoint in the default class constructor, set it on the first line of this class, since the default constructor is mapped to it.
https://www.jetbrains.com/help/idea/using-breakpoints.html
Simple test-case to determine breakpoint position:
public class ReflectionTest {
static int test = 1;
public static void main(String[] args) throws Exception {
System.out.println(ReflectionTest.class.getDeclaredConstructor().newInstance());
}
}
Placing the breakpoint on public class ReflectionTest seems to trigger for me.
Sometimes lint produces false warnins if field is operated via bunch of annotations. For a common example:
#SerializedName("id") #Expose private Integer id;
field id is assigned only via gson.fromJson(). Such operation is invisible for lint, thus it throws warning variable id is never assigned
So I want to configure lint, in this particular case, to ignore checks if field is ever assigned, if it is annotated with #SearializedName (please dont suggest raw #SuppressWarnings("unused") which has to be set manualy for every field and will block checks, if field is ever used)
Gson serialises fields using reflection, which takes place at runtime. That UnusedAssignment inspection finds variables which meet any of the following criteria:
the variable never gets read after assignment
the value is always overwritten with another assignment before the next variable read
the variable initializer is redundant (for one of the above two reasons) - the variable is never used.
Your only option to get rid of warnings for this specific inspection is to suppress them, either by updating your lint.xml, or via #SuppressWarnings("unused"). If you really don't want to do either of those things, then it may be possible to write a custom Lint inspection that ignores fields with a #SerializedName annotation.
The disadvantage of this approach is if you want to use #SerializedName in a class that isn't serialised by Gson, you will no longer get a warning if a variable is unused. It is also much more complicated than adding #SuppressWarnings("unused") to the top of your GSON model classes.