Difference in the declaration beyween two syntaxes - arrays

Ref : Cannot reference "X" before supertype constructor has been called, where x is a final variable
class ArrayFunctions {
//public Integer[] arrayTemplate;
private static Scanner scanner = new Scanner(System.in);
ArrayFunctions(int k){
Integer[] arrayTemplate = new Integer[k] ;
}
.
.
.
public class ArrayFunctionsImplementation{
public static void main(String[] args) {
ArrayFunctions newArray = new ArrayFunctions(5);
newArray.getIntegers(newArray.arrayTemplate);
newArray.printIntegers(newArray.arrayTemplate);
newArray.sortArray(newArray.arrayTemplate);
newArray.printIntegers(newArray.arrayTemplate);
}
}
}
If I use the declaration //public Integer[] arrayTemplate; that is currently commented out , I am able to access the variable "arrayTemplate" in the public class.
But if I declare the variable by calling the constructor as per the code below, I am unable to access it anywhere. If I understand correctly, both the ways declare the variable and by the time I am trying to access it , the object is already created.
PS : I am using Integer class just for experimentation instead of using plain int
Cheers

Your current code declares a variable of the ArrayFunctions constructor and so, that variable is only accessible in your constructor.
Your commented code, declares a member of the ArrayFunctions class, which then can be accessed anywhere from the class (or elsewhere since you made it public).

Related

How to initialize an array object

Why I am getting the error while runtime:
Exception in thread "main" java.lang.NullPointerException at arrayTest.main(arrayTest.java:5)
Source code is as following:
public class arrayTest{
int b;
public static void main(String[] args){
arrayTest[] a= new arrayTest[2];
a[0].b=10;
System.out.println(a[0].b);
}
}
Thanks
Sunil
You haven't added any arrayTest instances to your array. You've only initialized the array, so arrayTest[0] is null. To add objects to the array:
arrayTest[0] = new arrayTest();
arrayTest[1] = new arrayTest();
When doing Object-Oriented-Programming (OOP) you need to think a bit differently.
Here what you are doing is creating a new object arrayTest from the class arrayTest.
This object need a constructor and fields which are properties so it can be well defined for instance: size, age or eyes colour for a person.
Here what do you want your object to be?
For instance, I want to do an ArrayList of n object of the same type :
First, my field is going to be an ArrayList because that's what I want to create.
I have the following class :
import java.lang.reflect.Type;
import java.util.ArrayList;
class arrayTestType {
private final ArrayList arrayTest;
}
What should my constructor return?
Well, an array of type Type with n elements is ArrayList<Type>(n)
so my constructor should be written like this :
public arrayTestType(Type type, int length) {
arrayTest = new ArrayList<Type>(length);
}
So finally our class is :
import java.lang.reflect.Type;
import java.util.ArrayList;
class arrayTestType {
private final ArrayList arrayTest;
public arrayTestType(Type type, int length){
arrayTest = new ArrayList<Type>(length);
}
}
Now when we are going to call :
arrayTestType stringArrayOfLength5 = new arrayTestType<String>(5);
We are going to get an object well defined.
Now you need to add things in order for it not to be null hence the null pointer !
Good luck !

when assign static variable in a class, would that procedure run everytime we initialize new class?

I have the class
class CongNhan
{
public static decimal pr1= LoadFromDB(query1);
public static decimal pr2= LoadFromDB(query2);
public static int pr3= LoadFromBD(query3);
private string name;
public CongNhan()
{
name = "";
}
public CongNhan(string Name)
{
name = Name;
}
}
The question is how many times does 3 assigns to the static variables run. And if we new Class like: new CongNhan(), will it call three first assigns.
Because the static variables get value from Database so knowing how many times is it called is so much important to optimize and make it run faster.
Thank you!
AFAIK, static members of a class are initialized when app-domain with the class gets loaded into memory. So the three fields pr1, pr2, pr3 will be initialized once every time app-domain gets loaded. If you new up the class using new CongNhan(), those static fields will not be initialized again.

Need to verify size of an array in unit testing [duplicate]

This question already has answers here:
How do I test a class that has private methods, fields or inner classes?
(58 answers)
Closed 8 years ago.
Class Elem{
private ArrayList<someType> arr = new ArrayList<>();
public void addElement(someType var) {
arr.add(var);
}
public someType bestelement() {
someType first= arr.get(0);
arr.remove(0);
return first;
}
}
I have written test case for this method and it's running successfully but I need to know how can I be sure that the remove() method was called and the size of array list was reduced by 1? Please do tell me how to get the size of arr in my test case?
Test case for this method
Class ElemTest{
private Elem obj = new Elem();
private someType var1;
private someType var2;
private ArrayList<someType> testArr = new ArrayList<>();
#Test
public void bestElementTest() {
obj.addElement(var1);
obj.addElement(var2);
testArr.add(var1);
testArr.add(var2);
someType result = testArr.get(0);
assertEquals("test failed", result, obj.bestElem());
}
}
Given your example its difficult to advise you, but in general terms you options are to set the class into a known state, call you method which chnages the class and then check that the state has changed in the way you expect.
In this specific case if you have access to the internal list somewhere then you can check that the list has changed (ie the element has been removed). If you don't have access to the internal list then you need to check other things, like:
if you call bestElement() again when the object contains more than 1 element you get a different element
if you call bestElement() again when the object should not have any more elements you get an exception
These obviously rely on being able to set the object into one of the above states and we don't know if that is possible from the sample.
My final piece of advise would be to focus the test on the behaviour that you want to see from your class, not in the implementation of how the class works.

JAX RS, I can't see arrays in json output

I'm a beginner with JAX RS architecture. I've made a simple class like this:
#XmlRootElement
public class DatoBase
{
private int _id;
private String _name;
private int[] _listId;
//...here all get and set methods
}
This class, as you can see has an array (_listId), correctly initialized.
I've made my web services, that correctly istantiate and POST a new element of DatoBase, and I've made a method to GET this element, that is:
#GET
#Produces("application/json")
#Path("{id}")
public DatoBase GetDato(#PathParam("id") int dId)
{
return dati.get(dId);
}
where dati is declared as:
private TreeMap<Integer,DatoBase> dati = new TreeMap<Integer,DatoBase>();
but when I try to get the element i've already posted, i see this structure:
{"id":"0","name":"Dato10"}
I can't see my _listId structure (initialized with 3 elements) in this output.
I expected an output like this:
{"id":"0","name":"Dato10","listId":[...]}
Could anyone help me or tell me why?
Thank you
You should annotate your array with #XmlElementWrapper.
#XmlElementWrapper
private int[] _listId;
See here for further reference.

How to share an Array between all Classes in an application?

I want to share an Array which all classes can "get" and "change" data inside that array. Something like a Global array or Multi Access array. How this is possible with ActionScript 3.0 ?
There are a couple of ways to solve this. One is to use a global variable (as suggested in unkiwii's answer) but that's not a very common approach in ActionScript. More common approaches are:
Class variable (static variable)
Create a class called DataModel or similar, and define an array variable on that class as static:
public class DataModel {
public static var myArray : Array = [];
}
You can then access this from any part in your application using DataModel.myArray. This is rarely a great solution because (like global variables) there is no way for one part of your application to know when the content of the array is modified by another part of the application. This means that even if your data entry GUI adds an object to the array, your data list GUI will not know to show the new data, unless you implement some other way of telling it to redraw.
Singleton wrapping array
Another way is to create a class called ArraySingleton, which wraps the actual array and provides access methods to it, and an instance of which can be accessed using the very common singleton pattern of keeping the single instance in a static variable.
public class ArraySingleton {
private var _array : Array;
private static var _instance : ArraySingleton;
public static function get INSTANCE() : ArraySingleton {
if (!_instance)
_instance = new ArraySingleton();
return _instance;
}
public function ArraySingleton() {
_array = [];
}
public function get length() : uint {
return _array.length;
}
public function push(object : *) : void {
_array.push(object);
}
public function itemAt(idx : uint) : * {
return _array[idx];
}
}
This class wraps an array, and a single instance can be accessed through ArraySingleton.INSTANCE. This means that you can do:
var arr : ArraySingleton = ArraySingleton.INSTANCE;
arr.push('a');
arr.push('b');
trace(arr.length); // traces '2'
trace(arr.itemAt(0)); // trace 'a'
The great benefit of this is that you can dispatch events when items are added or when the array is modified in any other way, so that all parts of your application can be notified of such changes. You will likely want to expand on the example above by implementing more array-like interfaces, like pop(), shift(), unshift() et c.
Dependency injection
A common pattern in large-scale application development is called dependency injection, and basically means that by marking your class in some way (AS3 meta-data is often used) you can signal that the framework should "inject" a reference into that class. That way, the class doesn't need to care about where the reference is coming from, but the framework will make sure that it's there.
A very popular DI framework for AS3 is Robotlegs.
NOTE: I discourage the use of Global Variables!
But here is your answer
You can go to your default package and create a file with the same name of your global variable and set the global variable public:
//File: GlobalArray.as
package {
public var GlobalArray:Array = [];
}
And that's it! You have a global variable. You can acces from your code (from anywhere) like this:
function DoSomething() {
GlobalArray.push(new Object());
GlobalArray.pop();
for each (var object:* in GlobalArray) {
//...
}
}
As this question was linked recently I would add something also. I was proposed to use singleton ages ago and resigned on using it as soon as I realized how namespaces and references work and that having everything based on global variables is bad idea.
Aternative
Note this is just a showcase and I do not advice you to use such approach all over the place.
As for alternative to singleton you could have:
public class Global {
public static const myArray:Alternative = new Alternative();
}
and use it almost like singleton:
var ga:Alternative = Global.myArray;
ga.e.addEventListener(GDataEvent.NEW_DATA, onNewData);
ga.e.addEventListener(GDataEvent.DATA_CHANGE, onDataChange);
ga.push(0, 1, 2, 3, 4, 5, 6, 7, 8, 9, "ten");
trace(ga[5]); // 5
And your Alternative.as would look similar to singleton one:
package adnss.projects.tchqs
{
import flash.utils.Proxy;
import flash.utils.flash_proxy;
public class Alternative extends Proxy
{
private var _data:Array = [];
private var _events:AltEventDisp = new AltEventDisp();
private var _dispatching:Boolean = false;
public var blockCircularChange:Boolean = true;
public function Alternative() {}
override flash_proxy function getProperty(id:*):* {var i:int = id;
return _data[i += (i < 0) ? _data.length : 0];
//return _data[id]; //version without anal item access - var i:int could be removed.
}
override flash_proxy function setProperty(id:*, value:*):void { var i:int = id;
if (_dispatching) { throw new Error("You cannot set data while DATA_CHANGE event is dipatching"); return; }
i += (i < 0) ? _data.length : 0;
if (i > 9 ) { throw new Error ("You can override only first 10 items without using push."); return;}
_data[i] = value;
if (blockCircularChange) _dispatching = true;
_events.dispatchEvent(new GDataEvent(GDataEvent.DATA_CHANGE, i));
_dispatching = false;
}
public function push(...rest) {
var c:uint = -_data.length + _data.push.apply(null, rest);
_events.dispatchEvent(new GDataEvent(GDataEvent.NEW_DATA, _data.length - c, c));
}
public function get length():uint { return _data.length; }
public function get e():AltEventDisp { return _events; }
public function toString():String { return String(_data); }
}
}
import flash.events.EventDispatcher;
/**
* Dispatched after data at existing index is replaced.
* #eventType adnss.projects.tchqs.GDataEvent
*/
[Event(name = "dataChange", type = "adnss.projects.tchqs.GDataEvent")]
/**
* Dispatched after new data is pushed intwo array.
* #eventType adnss.projects.tchqs.GDataEvent
*/
[Event(name = "newData", type = "adnss.projects.tchqs.GDataEvent")]
class AltEventDisp extends EventDispatcher { }
The only difference form Singleton is that you can actually have multiple instances of this class so you can reuse it like this:
public class Global {
public static const myArray:Alternative = new Alternative();
public static const myArray2:Alternative = new Alternative();
}
to have two separated global arrays or even us it as instance variable at the same time.
Note
Wrapping array like this an using methods like myArray.get(x) or myArray[x] is obviously slower than accessing raw array (see all additional steps we are taking at setProperty).
public static const staticArray:Array = [1,2,3];
On the other hand you don't have any control over this. And the content of the array can be changed form anywhere.
Caution about events
I would have to add that if you want to involve events in accessing data that way you should be careful. As with every sharp blade it's easy to get cut.
For example consider what happens when you do this this:
private function onDataChange(e:GDataEvent):void {
trace("dataChanged at:", e.id, "to", Global.myArray[e.id]);
Global.myArray[e.id]++;
trace("new onDataChange is called before function exits");
}
The function is called after data in array was changed and inside that function you changing the data again. Basically it's similar to doing something like this:
function f(x:Number) {
f(++x);
}
You can see what happens in such case if you toggle myArray.blockCircularChange. Sometimes you would intentionally want to have such recursion but it is likely that you will do it "by accident". Unfortunately flash will suddenly stop such events dispatching without even telling you why and this could be confusing.
Download full example here
Why using global variables is bad in most scenarios?
I guess there is many info about that all over the internet but to be complete I will add simple example.
Consider you have in your app some view where you display some text, or graphics, or most likely game content. Say you have chess game. Mayby you have separated logic and graphics in two classes but you want both to operate on the same pawns. So you create your Global.pawns variable and use that in both Grahpics and Logic class.
Everything is randy-dandy and works flawlessly. Now You come with the great idea - add option for user to play two matches at once or even more. All you have to do is to create another instance of your match... right?
Well you are doomed at this point because, every single instance of your class will use the same Global.pawns array. You not only have this variable global but also you have limited yourself to use only single instance of each class that use this variable :/
So before you use any global variables, just think twice if the thing you want to store in it is really global and universal across your entire app.

Resources