Suppose we want to write a macro that defines an anonymous class with some type members or methods, and then creates an instance of that class that's statically typed as a structural type with those methods, etc. This is possible with the macro system in 2.10.0, and the type member part is extremely easy: - object MacroExample extends ReflectionUtils {
-
import scala.language.experimental.macros
-
import scala.reflect.macros.Context
-
-
def foo(name: String): Any = macro foo_impl
-
def foo_impl(c: Context)(name: c.Expr[String]) = {
-
import c.universe._
-
-
val Literal(Constant(lit: String)) = name.tree
-
val anon = newTypeName(c.fresh)
-
-
c.Expr(Block(
-
ClassDef(
-
Modifiers(Flag.FINAL), anon, Nil, Template(
-
Nil, emptyValDef, List(
-
constructor(c.universe),
-
TypeDef(Modifiers(), newTypeName(lit), Nil, TypeTree(typeOf[Int]))
-
)
-
)
-
),
-
Apply(Select(New(Ident(anon)), nme.CONSTRUCTOR), Nil)
-
))
-
}
-
}
(Where ReflectionUtils is a convenience trait that provides my constructor method.)
This macro lets us specify the name of the anonymous class's type member as a string literal: - scala> MacroExample.foo("T")
-
res0: AnyRef{type T = Int} = $1$$1@7da533f6
Note that it's appropriately typed. We can confirm that everything's working as expected: - scala> implicitly[res0.T =:= Int]
-
res1: =:=[res0.T,Int] = <function1>
-
Now suppose that we try to do the same thing with a method: - def bar(name: String): Any = macro bar_impl
-
def bar_impl(c: Context)(name: c.Expr[String]) = {
-
import c.universe._
-
-
val Literal(Constant(lit: String)) = name.tree
-
val anon = newTypeName(c.fresh)
-
-
c.Expr(Block(
-
ClassDef(
-
Modifiers(Flag.FINAL), anon, Nil, Template(
-
Nil, emptyValDef, List(
-
constructor(c.universe),
-
DefDef(
-
Modifiers(), newTermName(lit), Nil, Nil, TypeTree(),
-
c.literal(42).tree
-
)
-
)
-
)
-
),
-
Apply(Select(New(Ident(anon)), nme.CONSTRUCTOR), Nil)
-
))
-
}
But when we try it out, we don't get a structural type - scala> MacroExample.bar("test")
-
res1: AnyRef = $1$$1@da12492
But if we stick an extra anonymous class in there: - def baz(name: String): Any = macro baz_impl
-
def baz_impl(c: Context)(name: c.Expr[String]) = {
-
import c.universe._
-
-
val Literal(Constant(lit: String)) = name.tree
-
val anon = newTypeName(c.fresh)
-
val wrapper = newTypeName(c.fresh)
-
-
c.Expr(Block(
-
ClassDef(
-
Modifiers(), anon, Nil, Template(
-
Nil, emptyValDef, List(
-
constructor(c.universe),
-
DefDef(
-
Modifiers(), newTermName(lit), Nil, Nil, TypeTree(),
-
c.literal(42).tree
-
)
-
)
-
)
-
),
-
ClassDef(
-
Modifiers(Flag.FINAL), wrapper, Nil,
-
Template(Ident(anon) :: Nil, emptyValDef, constructor(c.universe) :: Nil)
-
),
-
Apply(Select(New(Ident(wrapper)), nme.CONSTRUCTOR), Nil)
-
))
-
}
It works: - scala> MacroExample.baz("test")
-
res0: AnyRef{def test: Int} = $2$$1@6663f834
-
-
scala> res0.test
-
res1: Int = 42
This is extremely handy—it lets you do things like this, for example—but I don't understand why it works, and the type member version works, but not bar. I know this may not be defined behavior, but does it make any sense? Is there an cleaner way to get a structural type (with the methods on it) from a macro?
0 2229 Sign in to post your reply or Sign up for a free account.
Similar topics |
by: fotzor |
last post by:
Hi,
is it somehow possible to get the type of a variable in a macro?
example:
#define SOME_MACRO(x) // what's the type of x???
i guess the type-information is lost but i can't use a template here
|
by: bittercold |
last post by:
Hi, guys,
I need to overload global "new" operator but I have to know the type id
"new" is begin invoked on.
For example if I overload it like this
void *operator new(size_t n)
{
...body...
}
|
by: Michael McGarry |
last post by:
Hi,
I am pretty sure this is not possible, but maybe somehow it is.
Given a variable, can I tell what type it is at runtime?
Michael
|
by: jester |
last post by:
For debugging purposes, I'm trying to programmatically retrieve the user
account name for the anonymous and impersonated account. Using
User.Identity.Name didn't do the trick. Any ideas? Thanks =)
|
by: WakeBdr |
last post by:
I'm writing a class that will query a database for some data and return
the result to the caller. I need to be able to return the result of
the query in several different ways: list, xml, dictionary, etc. I was
wondering if I can use decorators to accomplish this.
For instance, I have the following method
def getUsers(self, params):
return users.query(dbc)
| |
by: emmaruwa |
last post by:
The following VBA code, in Access 2003, is to make a button open and populate a form based on the Surname and Period_frm data on a previous form. However, i keep getting a type mismatch error whenever i click the button. I've tried changing the stLinkCriteria2 type to String but the same thing happens. Does anyone know why?
Private Sub IndividualRpt_Click()
On Error GoTo Err_Command12_Click
Dim stDocName As String
Dim...
|
by: David Resnick |
last post by:
I'm faced with a header with anonymous structures declared inside a
union like this:
union msg {
struct {
int a;
int b;
} s1;
struct {
|
by: andreyvul |
last post by:
If I try compiling this in gcc, it says: "error: request for member
`baz' in something not a structure or union".
Any workarounds or tips on how to make a structure such that it
behaves like an enum but its members can be addressed with '.'?
I don't want to have to do this using #defines, as it would be far too
messy.
code:
static struct {
static const int baz = 1;
} bar;
|
by: philly_bob |
last post by:
In the sample program below, I want to send a random method to a class
instance.
In other words, I don't know which method to send until run-time. How
can I send ch, which is my random choice, to the myclass instance?
Thanks,
Bob=
####
|
by: DonRayner |
last post by:
This one has me stumped. I'm getting a "Type Mismatch" error on one of my forms when it's being opened. It's hapening before the forms "On Open" event, I stuck a msgbox in there to check and I'm getting the error before it opens.
The line of code that calls the form from another form is.
DoCmd.OpenForm "NonConformanceAdd",,,,acFormAdd,acDialog
I get the error, click ok, then the form opens and works exactly how it's supposed to. I even...
|
by: Oralloy |
last post by:
Hello folks,
I am unable to find appropriate documentation on the type promotion of bit-fields when using the generalised comparison operator "<=>".
The problem is that using the GNU compilers, it seems that the internal comparison operator "<=>" tries to promote arguments from unsigned to signed.
This is as boiled down as I can make it.
Here is my compilation command:
g++-12 -std=c++20 -Wnarrowing bit_field.cpp
Here is the code in...
| |
by: jinu1996 |
last post by:
In today's digital age, having a compelling online presence is paramount for businesses aiming to thrive in a competitive landscape. At the heart of this digital strategy lies an intricately woven tapestry of website design and digital marketing. It's not merely about having a website; it's about crafting an immersive digital experience that captivates audiences and drives business growth.
The Art of Business Website Design
Your website is...
|
by: Hystou |
last post by:
Overview:
Windows 11 and 10 have less user interface control over operating system update behaviour than previous versions of Windows. In Windows 11 and 10, there is no way to turn off the Windows Update option using the Control Panel or Settings app; it automatically checks for updates and installs any it finds, whether you like it or not. For most users, this new feature is actually very convenient. If you want to control the update process,...
|
by: agi2029 |
last post by:
Let's talk about the concept of autonomous AI software engineers and no-code agents. These AIs are designed to manage the entire lifecycle of a software development project—planning, coding, testing, and deployment—without human intervention. Imagine an AI that can take a project description, break it down, write the code, debug it, and then launch it, all on its own....
Now, this would greatly impact the work of software developers. The idea...
|
by: conductexam |
last post by:
I have .net C# application in which I am extracting data from word file and save it in database particularly. To store word all data as it is I am converting the whole word file firstly in HTML and then checking html paragraph one by one.
At the time of converting from word file to html my equations which are in the word document file was convert into image.
Globals.ThisAddIn.Application.ActiveDocument.Select();...
|
by: TSSRALBI |
last post by:
Hello
I'm a network technician in training and I need your help.
I am currently learning how to create and manage the different types of VPNs and I have a question about LAN-to-LAN VPNs.
The last exercise I practiced was to create a LAN-to-LAN VPN between two Pfsense firewalls, by using IPSEC protocols.
I succeeded, with both firewalls in the same network. But I'm wondering if it's possible to do the same thing, with 2 Pfsense firewalls...
|
by: 6302768590 |
last post by:
Hai team
i want code for transfer the data from one system to another through IP address by using C# our system has to for every 5mins then we have to update the data what the data is updated we have to send another system
| |
by: muto222 |
last post by:
How can i add a mobile payment intergratation into php mysql website.
|
by: bsmnconsultancy |
last post by:
In today's digital era, a well-designed website is crucial for businesses looking to succeed. Whether you're a small business owner or a large corporation in Toronto, having a strong online presence can significantly impact your brand's success. BSMN Consultancy, a leader in Website Development in Toronto offers valuable insights into creating effective websites that not only look great but also perform exceptionally well. In this comprehensive...
| |