|
From: William S F. <ws...@fu...> - 2007-10-12 23:05:12
|
William S Fulton wrote:
> David Piepgrass wrote:
>>>> The problem is, the MT_ prefix is not needed in C# because every use
>> of
>>>> an enum must be qualified. I would like to eliminate the prefix so I
>>>> made this partial solution:
>>>>
>>> Hello David,
>>> One idea would be to use the rename function
>>> %rename(Circle) MT_Circle;
>>> %rename(Square) MT_Square;
>>> etc.
>>>
>>> You could use a macro to help you.
>>>
>>> #define RENAME_ENUM(X) %rename(X) MT_ ## X;
>>> RENAME_ENUM(Circle)
>>> RENAME_ENUM(Square)
>>> etc.
>>
>> I wonder if you read my entire message.
>>
>> I'm afraid your suggestion doesn't avoid any name collisions. The
>> following does not work at all, for example.
>>
>> %rename(Foo) TOT_Foo;
>> %rename(Bar) TOT_Bar;
>> %rename(Foo) F_Foo;
>> %rename(Bar) F_Bar;
>>
>> enum TypesOfThings {
>> TOT_Foo,
>> TOT_Bar,
>> };
>> enum Foozies {
>> F_Foo,
>> F_Bar
>> };
>> class Foo {
>> };
>> class Bar {
>> };
>>
>
> Your code above is equivalent to:
>
> enum TypesOfThings {
> Foo,
> Bar,
> };
> enum Foozies {
> Foo,
> Bar
> };
> class Foo {
> };
> class Bar {
> };
>
> If you try and compile this with a c++ compiler, it won't like the two
> enum values called Foo as they are in the same namespace. You also
> won't be able to instantiate the class Foo due to conflict with the
> enum value Foo. In some languages like C#, the enum values are
> qualified by the enum type (only if wrapping using typesafe enums or
> proper enums). In some scripting languages this is not the case as
> well as when wrapping using simple enums for C#. SWIG is largely using
> the C++ namespace to detect name collisions and as advertised, it
> flattens all the symbols into the same namespace, so you cannot wrap
> the following valid C++ without intervention:
>
> // C++
> namespace Space1 { class Bar {}; }
> namespace Space2 { class Bar {}; }
>
> even though in C# you could have
>
> namespace Space1 { public class Bar {}; }
> namespace Space2 { public class Bar {}; }
>
> as far as SWIG is concerned this is:
>
> public class Bar {};
> public class Bar {};
>
> so the documented solution is to use %rename, and not to rename them
> to symbol names that already exist.
>
> Saying all that, there might be a bug (it isn't clear to me) as given
> the following:
>
> enum TypesOfThings {
> Foo,
> Bar,
> };
> class Bar {
> };
>
> My C++ compiler will not compile:
>
> Bar b;
>
> but it will compile:
>
> TypesOfThings t = Bar;
>
> SWIG's symbol table should mirror that of C++, but here it isn't clear
> as to what should be in the C++ symbol table. Hours of reading the C++
> standard will probably give you some idea, but in all likelihood
> confuse you even more :)
Actually, there is an inconsistency here as with the following SWIG is
not flattening the namespaces for the enum values:
namespace Space1 {
enum TypesOfThings {
Foo,
Bar,
};
}
namespace Space2 {
enum Foozies {
Foo,
Bar
};
}
It does not warn about duplicate Foo, but it does with:
%rename(Foo) TOT_Foo;
%rename(Bar) TOT_Bar;
%rename(Foo) F_Foo;
%rename(Bar) F_Bar;
enum TypesOfThings {
TOT_Foo,
TOT_Bar,
};
enum Foozies {
F_Foo,
F_Bar
};
Sorry, this isn't really providing any solutions to your problem, other
than you could possibly use namespaces to rewrite your C++ code to solve
the problem.
William
|