Eclipse Community Forums
Forum Search:

Search      Help    Register    Login    Home
Home » Modeling » VIATRA2 » Please criticise my transformation
Please criticise my transformation [message #645339] Thu, 16 December 2010 11:57 Go to previous message
Tassilo Horn is currently offline Tassilo Horn
Messages: 86
Registered: July 2009
Member
Hi all,

I've finished my first transformation. It's a slight extension of the
ATL tutorial's Families2Persons transformation. Basically, on the
source side there are Families connected to Members with different
relations (father, mother, sons, daughters), and on the target side,
there are Males and Females with an abstract supertype Person, and
a Male relates to his wife, and parents to their children.

My transformation seems to work properly (at least, I get what I
expect), but since it is my first self-made VIATRA2 transformation, I'd
be very happy for comments and improvement suggestions!

Especially, the transformation seem overly verbose to me because of
pretty much code duplication (like in the childParentMapping pattern).

The complete eclipse project containing the model space and the
transformation can be downloaded from

http://www.uni-koblenz.de/~horn/Families2PersonsVIATRA2.tar. gz

Ok, so this is my code:

--8<---------------cut here---------------start------------->8---
namespace familymodel2genealogy;

import Families.metamodel;
import Persons.metamodel;

machine FamilyModel2Genealogy {

// ENTRY POINT

rule main() = call transform();

// PATTERNS

pattern memberMapping(M, P) = {
Member(M);
Person(P);
Member.member2person(Traces, M, P);
}

pattern maleMemberMapping(M, P) = {
Male(P);
find memberMapping(M, P);
}

pattern femaleMemberMapping(M, P) = {
Female(P);
find memberMapping(M, P);
}

pattern familyModelMapping(FM, G) = {
FamilyModel(FM);
Genealogy(G);
FamilyModel.familymodel2genealogy(Traces, FM, G);
}

pattern isFemale(M) = {
Member(M);
Family(SomeFamily);
Family.mother(X, SomeFamily, M);
} or {
Member(M);
Family(SomeFamily);
Family.daughters(X, SomeFamily, M);
}

pattern familyMapping(F, A) = {
Family(F);
Address(A);
Family.family2address(X, F, A);
}

pattern childParentMapping(C, PC, PP) = {
Member(C);
find memberMapping(C, PC);
Family(Fam);
Family.sons(S, Fam, C);
Member(P);
Family.father(X, Fam, P);
find memberMapping(P, PP);
} or {
Member(C);
find memberMapping(C, PC);
Family(Fam);
Family.daughters(S, Fam, C);
Member(P);
Family.father(X, Fam, P);
find memberMapping(P, PP);
} or {
Member(C);
find memberMapping(C, PC);
Family(Fam);
Family.daughters(S, Fam, C);
Member(P);
Family.mother(X, Fam, P);
find memberMapping(P, PP);
} or {
Member(C);
find memberMapping(C, PC);
Family(Fam);
Family.sons(S, Fam, C);
Member(P);
Family.mother(X, Fam, P);
find memberMapping(P, PP);
}

pattern mappedChild(PC, PP) = {
Person(PC);
Person(PP);
Person.children(X, PP, PC);
}

pattern mainFamily(M, F) = {
Member(M);
Family(F);
Family.father(X, F, M);
} or {
Member(M);
Family(F);
Family.mother(X, F, M);
} or {
Member(M);
Family(F);
Family.sons(X, F, M);
} or {
Member(M);
Family(F);
Family.daughters(X, F, M);
}

// GT RULES

gtrule transformFamilyModel(out FM, out G) = {
precondition pattern unmappedFamilyModel(FM) = {
FamilyModel(FM);
neg find familyModelMapping(FM, NoGenealogy);
}
postcondition
find familyModelMapping(FM, G)
action {
move(G, Persons.model);
rename(G, name(FM) + "Genealogy");
call members2Persons(FM, G);
call families2Addresses(FM, G);
call createRelations(FM);
}
}

gtrule transformFamily(out F, in G) = {
precondition pattern unmappedFamily(F, S, T, G) = {
Family(F);
Genealogy(G);
neg find familyMapping(F, NoAddress);
Family.street(S) in F;
Family.town(T) in F;
}
postcondition pattern mappedFamily(F, A, G) = {
find familyMapping(F, A);
Genealogy(G);
}
action {
move(A, Persons.model);
rename(A, name(F) + "Address");
let Street = undef, Town = undef in seq {
new(Address.street(Street) in A);
new(Address.town(Town) in A);
setValue(Street, value(S));
setValue(Town, value(T));
}
}
}

gtrule transformMaleMember(out M, in G) = {
precondition pattern unmappedMember(M, FN, LN, G) = {
Member(M);
Family(F);
Member.firstName(FN) in M;
find mainFamily(M, F);
Family.lastName(LN) in F;
Genealogy(G);
neg find isFemale(M);
neg find memberMapping(M, NoPerson);
}
postcondition pattern mappedMember(M, P, G) = {
find maleMemberMapping(M, P);
Person(P);
Genealogy(G);
Genealogy.persons(X, G, P);
}
action {
move(P, Persons.model);
rename(P, name(M));
let FullName = undef in seq {
new(Person.fullName(FullName) in P);
setValue(FullName, value(FN) + " " + value(LN));
}
}
}

gtrule transformFemaleMember(out M, in G) = {
precondition pattern unmappedMember(M, FN, LN, G) = {
Member(M);
Family(F);
Member.firstName(FN) in M;
find mainFamily(M, F);
Family.lastName(LN) in F;
Genealogy(G);
find isFemale(M);
neg find memberMapping(M, NoPerson);
}
postcondition pattern mappedMember(M, P, G) = {
find femaleMemberMapping(M, P);
Person(P);
Genealogy(G);
Genealogy.persons(X, G, P);
}
action {
move(P, Persons.model);
rename(P, name(M));
let FullName = undef in seq {
new(Person.fullName(FullName) in P);
setValue(FullName, value(FN) + " " + value(LN));
}
}
}

gtrule connectSpouse(out H) = {
precondition pattern husband(H, W, PH, PW) = {
Member(H);
Member(W);
Male(PH);
Female(PW);
find maleMemberMapping(H, PH);
find femaleMemberMapping(W, PW);
neg find isFemale(H);
find isFemale(W);
Family(Family);
Family.father(X, Family, H);
Family.mother(X2, Family, W);
}
postcondition pattern spouse(PH, PW) = {
Male(PH);
Female(PW);
Male.wife(S, PH, PW);
}
}

gtrule connectMemberToAddress(out M) = {
precondition pattern familyMember(M, P, A) = {
Member(M);
Person(P);
find memberMapping(M, P);
Address(A);
Family(F);
find mainFamily(M, F);
find familyMapping(F, A);
}
postcondition pattern livesAt(P, A) = {
Person(P);
Address(A);
Person.address(X, P, A);
}
}

gtrule connectParents(out C) = {
precondition pattern unconnectedChild(C, PC, PP) = {
Member(C);
Person(PC);
Person(CC);
find childParentMapping(C, PC, PP);
neg find mappedChild(PC, PP);
}
postcondition pattern connectedChild(C, PC, PP) = {
Member(C);
Person(PC);
Person(PP);
Person.children(HC, PP, PC);
}
}

// ASM RULES

rule transform() = seq {
let G = undef in
forall FM with apply transformFamilyModel(FM, G)
do println("Transformed " + fqn(FM) + " to " + fqn(G));

println("--- Transformation terminated. ");
}

rule members2Persons(in FM, in G) = seq {
forall MMember in FM with apply transformMaleMember(MMember, G)
do println("Transformed " + fqn(MMember));
forall FMember in FM with apply transformFemaleMember(FMember, G)
do println("Transformed " + fqn(FMember));
}

rule families2Addresses(in FM, in G) = seq {
forall Family in FM with apply transformFamily(Family, G)
do println("Transformed " + fqn(Family));
}

rule createRelations(in FM) = seq {
forall Member in FM with apply connectSpouse(Member)
do println("Connected spouse of " + fqn(Member));
forall Member in FM with apply connectMemberToAddress(Member)
do println("Connected Address of " + fqn(Member));
iterate call connectChildrenToParents(FM);
}

rule connectChildrenToParents(in FM) = seq {
choose Child in FM with apply connectParents(Child)
do println("Connected parents of " + fqn(Child));
}
}
--8<---------------cut here---------------end--------------->8---

Thank a lot for any suggestions!

Bye,
Tassilo
--
Dipl.-Inform. Tassilo Horn | Room: B015
University of Koblenz-Landau, Campus Koblenz | Phone: +49 (261) 287-2745
Institute for Software Technology | Mail: horn@uni-koblenz.de
Universitätsstr. 1, 56070 Koblenz, Germany |
 
Read Message
Read Message
Read Message
Read Message
Read Message
Previous Topic:Importing Ecore metamodel into Modelspace with VIATRA2 R3.1
Next Topic:basic question on transformation of UML to colored petri net
Goto Forum:
  


Current Time: Sun May 26 04:05:43 EDT 2013

Powered by FUDForum. Page generated in 0.01767 seconds