Identifier idents no member for child class - casting

I do a little project in Pascal and I have a problem.
I have 3 class (1 parent 2 child)
TGroup = class
...
end;
TUser = class(TGroup)
...
public
someVariableForUser: Integer;
...
end;
TAdmin = class(TGroup)
...
public
someVariableForAdmin: Integer;
...
end;
//And main program like this:
var
Person: TGroup;
begin
Person := TGroup.Create();
Person.someVariableForAdmin := 1;
And i get Error: identifier idents no member "someVariableForAdmin"
When I change var Person: TAdmin, so everything works fine.
Please help, Thanks alot.

This is exactly what should be expected. A TGroup instance has no knowledge of types that descend from it, or any fields or methods those descendants might declare. If you want to access something that's contained in TAdmin and it's descendents, you need to create an instance of TAdmin or one of it's descendents.
If you want to access something in a TAdmin, you have to create a TAdmin in the first place:
var
Person: TGroup;
begin
Person := TAdmin.Create;
(Person as TAdmin).someVariableForAdmin := 1;
end.
It's not clear from your question what exactly you're trying to accomplish. You might want to post another question explaining your desired goal, post some base code, and ask for help in changing it to reach that goal. (It's too late to edit this one for that, as that would change the entire meaning of the question after you've received multiple answers to it.)

Related

C++ - Class method changes member variable, but not in main

I have a Student class which stores a student's name and registration number. One of the private members of the Student class is a map which stores a student's module code (string), along with the mark for the module (float).
The class has an 'addMark' function which takes a module code and the mark for that module. If the module already exists in the map, the mark is overwritten. Otherwise, it is inserted into the map.
void Student::addMark(const string &module, float mark)
{
map<string, float>::iterator iter = marks.find(module);
if (iter != marks.end()){marks[module] = mark;}
else{marks.insert({module, mark});}
}
I have checked, and this seems to work inside that function.
In the main function, I have a vector markLine which stores each token of a line in a text file containing the marks. The first token (markLine.at(0)) is the registration number, the second token is the module code, and the third token is the mark. So the vector might look like the following for a line:
markLine = {10105, "CE101", 78.5};
Anyway, after reading a line and storing each token, the module mark needs to be stored for the correct student, so I use a for loop to go through all the students and see if their registration number matches. If it does, the mark is added:
for (Student st: studVect)
{
if (st.getRegNo() == markLine.at(0))
{
st.addMark(markLine.at(1), markLine.at(2));
}
}
But when I check afterwards to see if the marks have changed for a student, they have not.
I've googled around a lot and found some questions quite similar to mine, and I have a feeling that this is something to do with references, and a copy of marks being created. However, I'm not really sure where exactly I need to be using a reference. If anyone could point me in the right direction, I would be grateful.
You're working with a copy of the Student record.
Change
for (Student st: studVect)
to
for (Student &st: studVect)

Groovy: Accessing class fields via list

First, I'm sorry for asking such a dumb question, but quick googling didn't help me much...
I'm a Java delevoper and very new to Groovy. Consider the following code snippet:
class Person {
public String name
}
​def jack = new Person()
jack.name = "Jack"
​
def bob = new Person()
bob.name = "Bob"
def list = new java.util.ArrayList()
list.add(jack)
list.add(bob)
println list.name​
Executing it gives the following output (list of name field values for each Person in the list):
[Jack, Bob]
So my question is what the corresponding java code for calling list.name?
My assumption is that it translates to something like:
list.stream().map(person -> person.name).collect(Collectors.toList())
Can somebody explain what exactly happens when i call list.name?
Thanks in advance!
Your code
list.property
is the shortest way to write this. What groovy implies here is the use of the spread operator:
list*.property
(note the * there). And .property could be short here for .getProperty(), for an implicit call to the getter).
So your assumption is correct, that this is the eager collection of the values .getProperty() returns into an ArrayList.

Scala and JPA Results Lists

Scala noob i'm afraid:
I have the following declared class variable which will the objects I read from the database:
val options = mutable.LinkedList[DivisionSelectOption]()
I then use JPA to get a List of all rows from a table:
val divisionOptions = em.createNamedQuery("SelectOption.all", classOf[SelectOption]) getResultList
/* Wrap java List in Scala List */
val wrappedOptions = JListWrapper.apply(divisionOptions)
/* Store the wrappedOptions in the class variable */
options += wrappedOptions
However, the last line has an error:
Type Expected: String, actual JListWrapper[SelectOption]
Can anyone help with what I am doing wrong? I'm just trying to populate the options object with the result of the DB call.
Thanks
What (probably) is happening is that a JlistWrapper[SelectOption] isn't a DivisionSelectOption, so the method += isn't applicable to it. That being the case, it is trying other stuff, and giving a final error on this:
options = options + wrappedOptions
That is a rewriting Scala can do to make things like x += 1 work for var x. The + method is present on all objects, but it takes a String as parameter -- that's so one can write stuff like options + ":" and have that work as in Java. But since wrappedOptions isn't a String, it complains.
Roundabout and confusing, I know, and even Odersky regrets his decision with regards to +. Let that be a lesson: if you thing of adding a method to Any, think really hard before doing it.

Nhibernate, Criteria List as search parameters

Basically what I am trying to do is retrieve an officer. I call this method and pass a IList of Officer Ids. what I want to do it use that Ilist which will have a number of unique ids in it. to pull the one record for each id into a IList of officers which i return and do stuff with.
My problem is that I can not for the life of me figure out how to get the restrictions correct. so say the list has 3 , 6 , 9 and 12 in it it would get all of these records.
public IList<Officer> GetOfficer(IList<int> OfficerId)
{
return session.CreateCriteria<Officer>()
.Add(Restrictions.Eq("OfficerId", OfficerId))
.SetCacheable(true)
.List<Officer>();
}
any help would be greatly appreciated thanks
Solution should be in InExpression:
public IList<Officer> GetOfficer(IList<int> OfficerId)
{
return session.CreateCriteria<Officer>()
.Add(new NHibernate.Criterion.InExpression("OfficerId"
, OfficerId.Cast<object>().ToArray()))
.SetCacheable(true)
.List<Officer>();
}

Elegant way to distinct Path or Entry key

I have an application loading CAD data (Custom format), either from the local filesystem specifing an absolute path to a drawing or from a database.
Database access is realized through a library function taking the drawings identifier as a parameter.
the identifiers have a format like ABC 01234T56-T, while my paths a typical windows Paths (eg x:\Data\cadfiles\cadfile001.bin).
I would like to write a wrapper function Taking a String as an argument which can be either a path or an identifier which calls the appropriate functions to load my data.
Like this:
Function CadLoader(nameOrPath : String):TCadData;
My Question: How can I elegantly decide wether my string is an idnetifier or a Path to a file?
Use A regexp? Or just search for '\' and ':', which are not appearing in the Identifiers?
Try this one
Function CadLoader(nameOrPath : String):TCadData;
begin
if FileExists(nameOrPath) then
<Load from file>
else
<Load from database>
end;
I would do something like this:
function CadLoader(nameOrPath : String) : TCadData;
begin
if ((Pos('\\',NameOrPath) = 1) {UNC} or (Pos(':\',NameOrPath) = 2) { Path })
and FileExists(NameOrPath) then
begin
// Load from File
end
else
begin
// Load From Name
end;
end;
The RegEx To do the same thing would be: \\\\|.:\\ I think the first one is more readable.
In my opinion, the K.I.S.S. principle applies (or Keep It Simple Stupid!). Sounds harsh, but if you're absolutely certain that the combination :\ will never be in your identifiers, I'd just look for it on the 2nd position of the string. Keeps things understandable and readable. Also, one more quote:
Some people, when confronted with a
problem, think "I know, I'll use
regular expressions." Now they have
two problems. - Jamie Zawinski
You should pass in an additional parameter that says exactly what the identifier actually represents, ie:
type
CadLoadType = (CadFromPath, CadFromDatabase);
Function CadLoader(aType: CadLoadType; const aIdentifier: String): TCadData;
begin
case aType of
CadFromPath: begin
// aIdentifier is a file path...
end;
CadFromDatabase: begin
// aIdentifier is a database ID ...
end;
end;
end;
Then you can do this:
Cad := CadLoader(CadFromFile, 'x:\Data\cadfiles\cadfile001.bin');
Cad := CadLoader(CadFromDatabase, 'ABC 01234T56-T');