Thanks to visit codestin.com
Credit goes to github.com

Skip to content

Commit d39f9f6

Browse files
Konstantin-Posudevskiydenfromufa
authored and
denfromufa
committed
Fix conversion of 'float' and 'double' values (#487)
* Fix conversion of 'float' and 'double' values Fix problem of conversion 'float' and 'double' values in converter.cs. As there was a range check both for 'float' and 'double' values, which are less or greater than its 'MinValue' and 'MaxValue' accordingly, several values like 'float.NegativeInfinity', 'float.PositiveInfinity' and the same 'double' values cannot be converted from Python to .NET values. Add error check after 'PyFloat_AsDouble' call. Due to Python C API documentation, method 'PyFloat_AsDouble' can return '-1.0' upon failure. So it requires error check. This rule forces to check for error and throw exception in case of error. Add tests, which cover problem of conversion 'float' and 'double' values. Resolves: #486. * Fix failing 'test_double_conversion' test Fix incorrect part of 'test_double_conversion' test in test_conversion.py. An 'OverflowError' was expected for valid values, which represent Python 'inf' and '-inf'. The problem was identified with support of conversion for Python 'inf' and '-inf' to .NET System.Double PositiveInfinity and NegativeInfinity. See also: #487.
1 parent bfce5e2 commit d39f9f6

File tree

6 files changed

+58
-16
lines changed

6 files changed

+58
-16
lines changed

AUTHORS.md

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -27,6 +27,7 @@
2727
- Joe Frayne ([@jfrayne](https://github.com/jfrayne))
2828
- John Burnett ([@johnburnett](https://github.com/johnburnett))
2929
- Luke Stratman ([@lstratman](https://github.com/lstratman))
30+
- Konstantin Posudevskiy ([@konstantin-posudevskiy](https://github.com/konstantin-posudevskiy))
3031
- Matthias Dittrich ([@matthid](https://github.com/matthid))
3132
- Patrick Stewart ([@patstew](https://github.com/patstew))
3233
- Raphael Nestler ([@rnestler](https://github.com/rnestler))

CHANGELOG.md

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -20,6 +20,8 @@ This document follows the conventions laid out in [Keep a CHANGELOG][].
2020
- Fixed crash on exit of the Python interpreter if a python class
2121
derived from a .NET class has a `__namespace__` or `__assembly__`
2222
attribute (#481)
23+
- Fixed conversion of 'float' and 'double' values (#486)
24+
2325

2426
## [2.3.0][] - 2017-03-11
2527

src/embed_tests/Python.EmbeddingTest.csproj

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -84,6 +84,7 @@
8484
<Compile Include="pyimport.cs" />
8585
<Compile Include="pyinitialize.cs" />
8686
<Compile Include="pyrunstring.cs" />
87+
<Compile Include="TestConverter.cs" />
8788
<Compile Include="TestCustomMarshal.cs" />
8889
<Compile Include="TestExample.cs" />
8990
<Compile Include="TestPyAnsiString.cs" />

src/embed_tests/TestConverter.cs

Lines changed: 48 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,48 @@
1+
using NUnit.Framework;
2+
using Python.Runtime;
3+
4+
namespace Python.EmbeddingTest
5+
{
6+
public class TestConverter
7+
{
8+
[OneTimeSetUp]
9+
public void SetUp()
10+
{
11+
PythonEngine.Initialize();
12+
}
13+
14+
[OneTimeTearDown]
15+
public void Dispose()
16+
{
17+
PythonEngine.Shutdown();
18+
}
19+
20+
[Test]
21+
public void TestConvertSingleToManaged(
22+
[Values(float.PositiveInfinity, float.NegativeInfinity, float.MinValue, float.MaxValue, float.NaN,
23+
float.Epsilon)] float testValue)
24+
{
25+
var pyFloat = new PyFloat(testValue);
26+
27+
object convertedValue;
28+
var converted = Converter.ToManaged(pyFloat.Handle, typeof(float), out convertedValue, false);
29+
30+
Assert.IsTrue(converted);
31+
Assert.IsTrue(((float) convertedValue).Equals(testValue));
32+
}
33+
34+
[Test]
35+
public void TestConvertDoubleToManaged(
36+
[Values(double.PositiveInfinity, double.NegativeInfinity, double.MinValue, double.MaxValue, double.NaN,
37+
double.Epsilon)] double testValue)
38+
{
39+
var pyFloat = new PyFloat(testValue);
40+
41+
object convertedValue;
42+
var converted = Converter.ToManaged(pyFloat.Handle, typeof(double), out convertedValue, false);
43+
44+
Assert.IsTrue(converted);
45+
Assert.IsTrue(((double) convertedValue).Equals(testValue));
46+
}
47+
}
48+
}

src/runtime/converter.cs

Lines changed: 6 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -770,10 +770,14 @@ private static bool ToPrimitive(IntPtr value, Type obType, out object result, bo
770770
goto type_error;
771771
}
772772
double dd = Runtime.PyFloat_AsDouble(op);
773+
Runtime.CheckExceptionOccurred();
773774
Runtime.XDecref(op);
774775
if (dd > Single.MaxValue || dd < Single.MinValue)
775776
{
776-
goto overflow;
777+
if (!double.IsInfinity(dd))
778+
{
779+
goto overflow;
780+
}
777781
}
778782
result = (float)dd;
779783
return true;
@@ -785,11 +789,8 @@ private static bool ToPrimitive(IntPtr value, Type obType, out object result, bo
785789
goto type_error;
786790
}
787791
double d = Runtime.PyFloat_AsDouble(op);
792+
Runtime.CheckExceptionOccurred();
788793
Runtime.XDecref(op);
789-
if (d > Double.MaxValue || d < Double.MinValue)
790-
{
791-
goto overflow;
792-
}
793794
result = d;
794795
return true;
795796
}

src/tests/test_conversion.py

Lines changed: 0 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -466,17 +466,6 @@ def test_double_conversion():
466466
with pytest.raises(TypeError):
467467
ConversionTest().DoubleField = None
468468

469-
with pytest.raises(OverflowError):
470-
ConversionTest().DoubleField = 1.7976931348623159e308
471-
472-
with pytest.raises(OverflowError):
473-
ConversionTest().DoubleField = -1.7976931348623159e308
474-
475-
with pytest.raises(OverflowError):
476-
_ = System.Double(1.7976931348623159e308)
477-
478-
with pytest.raises(OverflowError):
479-
_ = System.Double(-1.7976931348623159e308)
480469

481470

482471
def test_decimal_conversion():

0 commit comments

Comments
 (0)