Applying ST to Antlr4-generated parse trees - antlr4

Generated accessors of parse tree context nodes do not conform getProperty()/isProperty()/hasProperty() standard. As a result, ST can’t be applied to the parse tree directly. There seems to be 3 alternatives to apply ST to the generated parse trees:
Create ST model adapter classes for each generated context node. Then ST can be applied directly to the generated parse tree. Duplicate work here is creating model adapters.
For every parse tree node create a wrapper node that conforms getProperty()/isProperty()/hasProperty() standard. Then ST can be applied to wrapper nodes. Duplicate work here is creating wrapper nodes. (In this case parse tree is not even required; auto-parse-tree construction could be turned off and wrapper (AST) nodes could be created in grammar actions).
Create a Visitor. Each visit*() instantiates an ST specific to a context node being visited, sets parameters (which could be STs returned by visiting child nodes or simple strings) and returns the ST. This is the option I’m currently using. Duplicate work here is creating visitor and assigning template parameters in code.
Is there an Antlr4 option that generates accessors of parse tree context nodes that conform getProperty()/isProperty()/hasProperty() standard? Or is there an ST4 option that allows it accessing property() instead of looking for getProperty()?
It would be nice to simply instantiate an ST template with a root context node as a parameter and let ST traverse the tree.

Just wanted to share a solution that almost avoids duplicate work while using approach #1 from my question.
Step 1: create a model adaptor that uses reflection to call a method that does not conform getProperty()/isProperty()/hasProperty() standard.
private static class MyModelAdaptor extends ObjectModelAdaptor {
#Override
public synchronized Object getProperty(Interpreter interp, ST self, Object o, Object property, String propertyName) throws STNoSuchPropertyException {
try {
return super.getProperty(interp, self, o, property, propertyName);
} catch (STNoSuchPropertyException noProperty) {
final Class<?> cls = o.getClass();
try {
return cls.getMethod(propertyName).invoke(o);
} catch (NoSuchMethodException | IllegalAccessException | InvocationTargetException e) {
throw noProperty;
}
}
}
}
Step 2: Register model adaptors
public static STGroup registerAdaptors(STGroup stg) {
final MyModelAdaptor adaptor = new MyModelAdaptor();
for (final Class<?> cls : MyParser.class.getDeclaredClasses()) {
if (isSubclassOf(cls, ParserRuleContext.class)) {
stg.registerModelAdaptor(cls, adaptor);
}
}
return stg;
}
Step 3: implement isSubclassOf() method so that registerAdaptors() compiles:
private static boolean isSubclassOf(Class<?> cls, Class<?> superCls) {
while (cls != null) {
if (cls == superCls) {
return true;
}
cls = cls.getSuperclass();
}
return false;
}

Related

Groovy ASTNode modifications does not reflect in the final class getting executed

Here is my usecase. I am running on version 2.1.6
I am trying to convert all array declarations to a more custom datatype which is not exposed to the end user.
For example:
def strr = new String[4] will be modified to def strr=new mycustomType(datatypeForString,4)
def str = [1,2,3] as String[] will be modified to def str=new myCustomType(dataTypeForString,list)
So far at the AST level, I registered a custom visitor and visitDeclarationExpression().
I am currently compiling the user script using custom GroovyClassLoader and executing it on the fly using myclassLoader.parseClass(usertext).newInstance().run()
When I am executing the above the sequence(compiling, loading, executing) the AST transformations are executed(verified through sys printls) but the final code execution does not reflect it.
Here is the snippet of the code that modifies the expression and sets it to the parent.
#Override
public void visitDeclarationExpression(DeclarationExpression expression) {
// TODO Auto-generated method stub
if (expression.getLeftExpression() instanceof VariableExpression
&& expression.getRightExpression() instanceof ArrayExpression) {
// Inspect the arrayExpressio
expression.setRightExpression(transformArrayExpression((ArrayExpression) expression.getRightExpression()));
}
else if (expression.getLeftExpression() instanceof VariableExpression
&& expression.getRightExpression() instanceof CastExpression) {
// Inspect the cast expression
expression.setRightExpression(transformCastExpression((CastExpression) expression.getRightExpression()));
}
super.visitDeclarationExpression(expression);
}
Any pointers?

Kotlin thread safe native lazy singleton with parameter

In java we can write thead-safe singletons using double Checked Locking & volatile:
public class Singleton {
private static volatile Singleton instance;
public static Singleton getInstance(String arg) {
Singleton localInstance = instance;
if (localInstance == null) {
synchronized (Singleton.class) {
localInstance = instance;
if (localInstance == null) {
instance = localInstance = new Singleton(arg);
}
}
}
return localInstance;
}
}
How we can write it in kotlin?
About object
object A {
object B {}
object C {}
init {
C.hashCode()
}
}
I used kotlin decompiler to get that
public final class A {
public static final A INSTANCE;
private A() {
INSTANCE = (A)this;
A.C.INSTANCE.hashCode();
}
static {
new A();
}
public static final class B {
public static final A.B INSTANCE;
private B() {
INSTANCE = (A.B)this;
}
static {
new A.B();
}
}
public static final class C {
public static final A.C INSTANCE;
private C() {
INSTANCE = (A.C)this;
}
static {
new A.C();
}
}
}
All of object have constructor invoke in static block. Based on it, we can think that it's not lazy.
Сlose to the right answer.
class Singleton {
companion object {
val instance: Singleton by lazy(LazyThreadSafetyMode.PUBLICATION) { Singleton() }
}
}
Decompiled:
public static final class Companion {
// $FF: synthetic field
private static final KProperty[] $$delegatedProperties = new KProperty[]{(KProperty)Reflection.property1(new PropertyReference1Impl(Reflection.getOrCreateKotlinClass(Singleton.Companion.class), "instance", "getInstance()Lru/example/project/tech/Singleton;"))};
#NotNull
public final Singleton getInstance() {
Lazy var1 = Singleton.instance$delegate;
KProperty var3 = $$delegatedProperties[0];
return (Singleton)var1.getValue();
}
private Companion() {
}
// $FF: synthetic method
public Companion(DefaultConstructorMarker $constructor_marker) {
this();
}
}
I hope Kotlin developers will make non reflection implementation in future...
Kotlin has an equivalent of your Java code, but more safe. Your double lock check is not recommended even for Java. In Java you should use an inner class on the static which is also explained in Initialization-on-demand holder idiom.
But that's Java. In Kotlin, simply use an object (and optionally a lazy delegate):
object Singletons {
val something: OfMyType by lazy() { ... }
val somethingLazyButLessSo: OtherType = OtherType()
val moreLazies: FancyType by lazy() { ... }
}
You can then access any member variable:
// Singletons is lazy instantiated now, then something is lazy instantiated after.
val thing = Singletons.something // This is Doubly Lazy!
// this one is already loaded due to previous line
val eager = Singletons.somethingLazyButLessSo
// and Singletons.moreLazies isn't loaded yet until first access...
Kotlin intentionally avoids the confusion people have with singletons in Java. And avoids the "wrong versions" of this pattern -- of which there are many. It instead provides the simpler and the safest form of singletons.
Given the use of lazy(), if you have other members each would individually be lazy. And since they are initialized in the lambda passed to lazy() you can do things that you were asking about for about customizing the constructor, and for each member property.
As a result you have lazy loading of Singletons object (on first access of instance), and then lazier loading of something (on first access of member), and complete flexibility in object construction.
See also:
lazy() function
Lazy thread safe mode options
Object declarations
As a side note, look at object registry type libraries for Kotlin that are similar to dependency injection, giving you singletons with injection options:
Injekt - I'm the author
Kodein - Very similar and good
Object declaration is exactly for this purpose:
object Singleton {
//singleton members
}
It is lazy and thread-safe, it initializes upon first call, much as Java's static initializers.
You can declare an object at top level or inside a class or another object.
For more info about working with objects from Java, please refer to this answer.
As to the parameter, if you want to achieve exactly the same semantics (first call to getInstance takes its argument to initialize the singleton, following calls just return the instance, dropping the arguments), I would suggest this construct:
private object SingletonInit { //invisible outside the file
lateinit var arg0: String
}
object Singleton {
val arg0: String = SingletonInit.arg0
}
fun Singleton(arg0: String): Singleton { //mimic a constructor, if you want
synchronized(SingletonInit) {
SingletonInit.arg0 = arg0
return Singleton
}
}
The main flaw of this solution is that it requires the singleton to be defined in a separate file to hide the object SingletonInit, and you cannot reference Singleton directly until it's initialized.
Also, see a similar question about providing arguments to a singleton.
I recently wrote an article on that topic.
TL;DR Here's the solution I came up to:
1) Create a SingletonHolder class. You only have to write it once:
open class SingletonHolder<out T, in A>(creator: (A) -> T) {
private var creator: ((A) -> T)? = creator
#Volatile private var instance: T? = null
fun getInstance(arg: A): T {
val i = instance
if (i != null) {
return i
}
return synchronized(this) {
val i2 = instance
if (i2 != null) {
i2
} else {
val created = creator!!(arg)
instance = created
creator = null
created
}
}
}
}
2) Use it like this in your singletons:
class MySingleton private constructor(arg: ArgumentType) {
init {
// Init using argument
}
companion object : SingletonHolder<MySingleton, ArgumentType>(::MySingleton)
}
The singleton initialization will be lazy and thread-safe.

Find MethodInvocation method bindings in JDT ASTVisitor

I have a java file which uses java.sql.Statement.execute as below.
public class Dummy
{
public void execute(String q) throws SQLException
{
...
Statement stmt = conn.createStatement();
...
stmt.execute(q);
...
}
}
My use case is I want to identify what are all the classes and their method names which use "Statement.execute(String)" using JDT ASTVisitor. Is this possible?
I found below entry using eclipse ASTView plugin.
method binding: Statement.execute(String)
How can I get this method binding value in my ASTVisitor.
I tried this.
#Override
public boolean visit(MethodInvocation node)
{
IMethodBinding iMethod = (IMethodBinding) node.resolveMethodBinding();
if(iMethod != null)
System.out.println("Binding "+iMethod.getName());
return super.visit(node);
}
but node.resolveMethodBinding() always returns null.
... i want to identify what are all the classes and its method names which using "Statement.execute(String)"
This sounds like a job for the org.eclipse.jdt.core.search.SearchEngine, which will produce the results much faster than traversing all your source files using a visitor.
... node.resolveMethodBinding() always returns null
This depends on how you obtained the AST. See, e.g., org.eclipse.jdt.core.dom.ASTParser.setResolveBindings(boolean)

c# Generics new() constraints with type: (new(T))

I'm building a little helper to turn EF4 objects to POCOs.
(I know there is AutoMapper, but I'm having a c# dilemma at this time)
How can I make this work (the where P: new(E) is not legal
I wish to make sure the P (POCO) class as a constructor that takes the E class
(hence handling the transformation)
How can I make this work ?
How can I make a generic function in C# that can take a new(type) constraint ?
public static List<P> ListConvert<E, P>(List<E> efList) where P: new(E)
{
List<P> pList = new List<P>();
foreach (E item in efList)
{
P myItem = new P(item);
pList.Add(myItem);
}
return pList;
There's no such constraint. What you can do is have an extra parameter:
public static List<P> ListConvert<E, P>(List<E> efList, Func<E, P> func)
That way it isn't required to be a constructor, but you can pass in a delegate which calls the constructor:
ListConvert(list, x => new Foo(x))
I have a blue-sky idea which would enable constructor constraints, called "static interfaces" - these would only be useful for generic constraints, but would also enable some operator use cases.
This is not possible. The new constraint only allows you to create objects via a public parameterless constructor.
There's no such thing as P : new(E), but you could have the caller supply a delegate that knows how to construct a P given an E:
public static List<P> ListConvert<E, P>(List<E> efList, Func<E, P> converter)
{
List<P> pList = new List<P>();
foreach (E item in efList)
{
P myItem = converter(item);
pList.Add(myItem);
}
return pList;
}
However, if you're doing this, you may as well use LINQ: efList.Select(e => new P(e)).ToList().

Adding different object types to a c# 4.0 collection

I have a function that returns objects of different types based on the parameter passed to this function.
Is it possible to add these different object types to a collection based on some identifier in C# 4.0?
Usually we do something like this
List or List
but i want one collection which can add object of any type.
Instead of just making a List<object> like other posters are recommending, you may want to define an interface eg IListableObject that contains a few methods that your objects need to implement. This will make any code using these objects much easier to write and will guard against unwanted objects getting into the collection down the line.
Yes, it is called object. Eg:
var objlist = new List<object>();
objlist.Add(1);
objlist.Add(true);
objlist.Add("hello");
You could use object[], List<object>, ArrayList, IEnumerable, ... but if those types have a common base type it would be better to stick to a strongly typed collection.
Really your collection should be as specific as you can make it. When you say
objects of different types
Do these objects have anything in common? Do they implement a common interface?
If so you you can specialise the list on that interface List<IMyInterface>
Otherwise List<object> will do what you want.
Update
No, not really.
I'm sorry but I'm going to question your design.
If you have a collection of different objects, how do you decide how to use one of the objects?
You're going to have a large switch statement switching on the type of the object, then you cast to a specific object and use it.
You also have have a similar switch statement in your factory method that creates the object.
One of the benefits of Object Orientation is that if you design your objects correctly then you don't need to do these large "If it's this object do this.Method(), if it's that object do that.OtherMethod()".
Can I ask, why are you putting different objects into the same collection? What's the benefit to you?
If you want a collection which can add objects of any type then List<object> is the most appropriate type.
Collections in earlier versions of C# (not generics) can contain any kind of objects. If they're value type, they will be boxed into object.
When you need to use them, you can just cast it to the original type.
You may use List<Type> to hold the type information, if that's what you want. And Type[], Hashtable, etc. are also fine. You can use typeof operator to get the type or use Object.GetType().
Also check out Dynamic type.
http://msdn.microsoft.com/en-us/library/dd264736.aspx
It will basically do the same thing.
My Suggestion:
public class ParamValue
{
object value = null;
public ParamValue(object val)
{
value = val;
}
public string AsString()
{
return value.ToString();
}
public int AsInt()
{
return int.Parse(value.ToString());
}
public int? AsNullableInt()
{
int n;
if (int.TryParse(value.ToString(), out n))
{
return n;
}
return null;
}
public bool AsBool()
{
return bool.Parse(value.ToString());
}
public bool? AsNullableBool()
{
bool b;
if (bool.TryParse(value.ToString(), out b))
{
return b;
}
return null;
}
}
public class Params
{
Dictionary<string, object> paramCol = new Dictionary<string, object>();
public void Add(string paramName, object value)
{
paramCol.Add(paramName, value);
}
public ParamValue this[string paramName]
{
get
{
object v;
if (paramCol.TryGetValue(paramName, out v))
{
return new ParamValue(v);
}
return null;
}
}
}
Use param class as a collectio to your values, you can convert the return to every type you want.
You could use a Tuple of Genric Types
public Tuple<T, T> MySuperMethod()
{
int number = 1;
string text = "Batman";
return new Tuple<int, string>(number, text);
}
The .NET Framework directly supports tuples with one to seven
elements. In addition, you can create tuples of eight or more elements
by nesting tuple objects in the Rest property of a Tuple object.
https://msdn.microsoft.com/en-us/library/system.tuple(v=vs.100).aspx

Resources