diff options
author | Ian Lance Taylor <iant@google.com> | 2011-05-27 00:04:32 +0000 |
---|---|---|
committer | Ian Lance Taylor <iant@google.com> | 2011-05-27 00:04:32 +0000 |
commit | 49532b718138f7b0188f0e7499010c72a3a89735 (patch) | |
tree | f7153e262ff36bf321203019d56f6a5e6c5de7bc /Doc | |
parent | 924be5044d2ec82ffa4d05ce5d8418aea378f1ff (diff) | |
download | swig-49532b718138f7b0188f0e7499010c72a3a89735.tar.gz |
Some improvements to the Go documentation. From Gary Holt
<gholt@google.com>.
git-svn-id: https://swig.svn.sourceforge.net/svnroot/swig/trunk@12719 626c5289-ae23-0410-ae9c-e8d60b6d4f22
Diffstat (limited to 'Doc')
-rw-r--r-- | Doc/Manual/Contents.html | 3 | ||||
-rw-r--r-- | Doc/Manual/Go.html | 160 |
2 files changed, 161 insertions, 2 deletions
diff --git a/Doc/Manual/Contents.html b/Doc/Manual/Contents.html index 04cbbcf2a..b53923c17 100644 --- a/Doc/Manual/Contents.html +++ b/Doc/Manual/Contents.html @@ -764,6 +764,8 @@ <li><a href="Go.html#Go_templates">Go Templates</a> <li><a href="Go.html#Go_director_classes">Go Director Classes</a> <li><a href="Go.html#Go_primitive_type_mappings">Default Go primitive type mappings</a> +<li><a href="#Go_output_arguments">Output arguments</a> +<li><a href="#Go_adding_additional_code">Adding additional go code</a> </ul> </ul> </div> @@ -1689,4 +1691,3 @@ </BODY> </HTML> - diff --git a/Doc/Manual/Go.html b/Doc/Manual/Go.html index 8681927c3..8c072e00a 100644 --- a/Doc/Manual/Go.html +++ b/Doc/Manual/Go.html @@ -28,6 +28,8 @@ <li><a href="#Go_templates">Go Templates</a> <li><a href="#Go_director_classes">Go Director Classes</a> <li><a href="#Go_primitive_type_mappings">Default Go primitive type mappings</a> +<li><a href="#Go_output_arguments">Output arguments</a> +<li><a href="#Go_adding_additional_code">Adding additional go code</a> </ul> </ul> </div> @@ -273,7 +275,7 @@ class. <p> SWIG will represent static methods of C++ classes as ordinary Go -functions. SWIG will use names like <tt>ClassName_MethodName</tt>. +functions. SWIG will use names like <tt>ClassNameMethodName</tt>. SWIG will give static members getter and setter functions with names like <tt>GetClassName_VarName</tt>. </p> @@ -289,6 +291,37 @@ to <tt>reinterpret_cast</tt>. This should only be used for very special cases, such as where C++ would use a <tt>dynamic_cast</tt>. </p> +<p>Note that C++ pointers to compound objects are represented in go as objects +themselves, not as go pointers. So, for example, if you wrap the following +function:</p> +<div class="code"> +<pre> +class MyClass { + int MyMethod(); + static MyClass *MyFactoryFunction(); +}; + +</pre> +</div> +<p>You will get go code that looks like this:</p> +<div class="code"> +<pre> +type MyClass interface { + Swigcptr() uintptr + SwigIsMyClass() + MyMethod() int +} + +MyClassMyFactoryFunction() MyClass { + // swig magic here +} +</pre> +</div> +<p>Note that the factory function does not return a go pointer; it actually +returns a go interface. If the returned pointer can be null, you can check +for this by calling the Swigcptr() method. +</p> + <H4><a name="Go_class_inheritance"></a>21.3.5.1 Go Class Inheritance</H4> @@ -459,5 +492,130 @@ that typemap, or add new values, to control how C/C++ types are mapped into Go types. </p> +<H3><a name="Go_output_arguments"></a>21.3.9 Output arguments</H3> + + +<p>Because of limitations in the way output arguments are processed in swig, +a function with output arguments will not have multiple return values. +Instead, you must pass a pointer into the C++ function to tell it where to +store the ouput value. In go, you supply a slice in the place of the output +argument.</p> + +<p>For example, suppose you were trying to wrap the modf() function in the +C math library which splits x into integral and fractional parts (and +returns the integer part in one of its parameters):<p> +<div class="code"> +<pre> +double modf(double x, double *ip); +</pre> +</div> +<p>You could wrap it with SWIG as follows:</p> +<div class="code"> +<pre> +%include <typemaps.i> +double modf(double x, double *OUTPUT); +</pre> +</div> +<p>or you can use the <code>%apply</code> directive:</p> +<div class="code"> +<pre> +%include <typemaps.i> +%apply double *OUTPUT { double *ip }; +double modf(double x, double *ip); +</pre> +</div> +<p>In Go you would use it like this:</p> +<div class="code"> +<pre> +ptr := []float64{0.0} +fraction := modulename.Modf(5.0, ptr) +</pre> +</div> +<p>Since this is ugly, you may want to wrap the swig-generated API with +some <a href="#Embedded_go_code">additional functions written in go</a> that +hide the ugly details.</p> + +<p>There are no <code>char *OUTPUT</code> typemaps. However you can +apply the <code>signed char *</code> typemaps instead:<p> +<div class="code"> +<pre> +%include <typemaps.i> +%apply signed char *OUTPUT {char *output}; +void f(char *output); +</pre> +</div> + +<H3><a name="Go_adding_additional_code"></a>21.3.10 Adding additional go code</H3> + +<p>Often the APIs generated by swig are not very natural in go, especially if +there are output arguments. You can +insert additional go wrapping code to add new APIs +with <code>%insert(go_wrapper)</code>, like this:</p> +<div class="code"> +<pre> +%include <typemaps.i> +// Change name of what swig generates to Wrapped_modf. This function will +// have the following signature in go: +// func Wrapped_modf(float64, []float64) float64 +%rename(wrapped_modf) modf(double x, double *ip); + +%apply double *OUTPUT { double *ip }; +double modf(double x, double *ip); + +%insert(go_wrapper) %{ + +// The improved go interface to this function, which has two return values, +// in the more natural go idiom: +func Modf(x float64) (fracPart float64, intPart float64) { + ip := []float64{0.0} + fracPart = Wrapped_modf(x, ip) + intPart = ip[0] + return +} + +%} +</pre> +</div> + +<p>For classes, since swig generates an interface, you can add additional +methods by defining another interface that includes the swig-generated +interface. For example,</p> +<div class="code"> +<pre> +%rename(Wrapped_MyClass) MyClass; +%rename(Wrapped_GetAValue) MyClass::GetAValue(int *x); +%apply int *OUTPUT { int *x }; + +class MyClass { + public: + MyClass(); + int AFineMethod(const char *arg); // Swig's wrapping is fine for this one. + bool GetAValue(int *x); +}; + +%insert(go_wrapper) %{ + +type MyClass interface { + Wrapped_MyClass + GetAValue() (int, bool) +} + +func (arg SwigcptrWrapped_MyClass) GetAValue() (int, bool) { + ip := []int{0} + ok := arg.Wrapped_GetAValue(ip) + return ip[0], ok +} + +%} +</pre> +</div> +<p>Of course, if you have to rewrite most of the methods, instead of just a +few, then you might as well define your own struct that includes the +swig-wrapped object, instead of adding methods to the swig-generated object.</p> + +<p>This only works if your wrappers do not need to import other go modules. +There is at present no way to insert import statements in the correct place +in swig-generated go. If you need to do that, you must put your go code +in a separate file.</p> </body> </html> |