Не работает должным образом в .Net MF - PullRequest
3 голосов
/ 10 января 2012

У меня есть что-то довольно странное, чтобы затушевывать цвета светодиодов RGB, и у меня возникают проблемы с получением желаемых значений.

Я сократил этот пример до минимума, но Start, End и Steps будут переменными ...

Это должно линейно увеличиваться R (UInt) от 0 до 255 за 100 шагов. Я не слишком беспокоюсь о точности здесь, поэтому мне все равно, правильно ли он округляется или просто делает Floor / Ceiling

    Dim Start As UInteger = 0
    Dim [End] As UInteger = 255
    Dim Steps = 100

    For x = 1 To Steps
        Dim Temp = ([End] - Start) / Steps * x + Start
        Dim R = CUInt(Temp)

        Debug.Print(x.ToString & ": Temp: " & Temp.ToString & ", R:" & R.ToString)
        LedR.SetPulse(255, R)
        Threading.Thread.Sleep(20)
    Next

Это выходы:

1: Temp: 2.5500, R:196608
2: Temp: 5.1000, R:327680
3: Temp: 7.6500, R:524288
4: Temp: 10.2000, R:655360
5: Temp: 12.7499, R:851968
...
95: Temp: 242.2488, R:15859712
96: Temp: 244.7988, R:16056320
97: Temp: 247.3488, R:16187392
98: Temp: 249.8988, R:16384000
99: Temp: 252.4488, R:16515072
100: Temp: 254.9988, R:16711680

Как видите, переменная Temp в значительной степени корректна, допускает некоторую небольшую неточность, но я не вижу, какова корреляция с R.

Возможно, что CUint просто читает биты для Temp и рассматривает Double как UInt - но если это так, как мне заставить его преобразовать его правильно?

(кстати, это работает на netduino ), .Net Micro Framework 4.2

Редактировать: Запрошенные ниже тесты:

    Dim Test As Integer = 2
    Debug.Print(Test.ToString)
    Debug.Print(CInt(Test).ToString)
    Debug.Print(CUInt(Test).ToString)

    2
    2
    2

    Dim Test As Double = 2.5
    Debug.Print(Test.ToString)
    Debug.Print(CInt(Test).ToString)
    Debug.Print(CUInt(Test).ToString)

    2.5000
    131072
    131072

Используя следующий код ...

    For x = 0 To Steps
        Dim Temp As Long = ([End] - Start) \ Steps * x + Start
        Dim R = CType(Temp, UInteger)

        Debug.Print(x.ToString & ": Temp: " & Temp.ToString & ", R:" & R.ToString)
        LedR.SetPulse(255, R)
        Threading.Thread.Sleep(20)
    Next

Я получаю (в строке Dim Temp):

An unhandled exception of type 'System.Exception' occurred in Netduino_VBTest.exe

Нет внутреннего исключения, но чуть выше него в выходных данных - исключение первого шанса, которое, как я предполагаю, является основной причиной:

A first chance exception of type 'System.NotImplementedException' occurred in Microsoft.SPOT.Native.dll

Ответы [ 4 ]

2 голосов
/ 10 января 2012

Попробуйте использовать Convert.ToUInt32, описанный здесь: http://msdn.microsoft.com/en-us/library/y3569ft9.aspx

На моем .Net 4.0 (не Micro) на Windows 7 64bit Я не вижу того, что вы видите с CInt / CUInt (мой конвертирует правильно).Это может быть ошибкой реализации в netduino / Micro Framework ... Если бы у меня это было, я бы проверил вышесказанное для вас.

1 голос
/ 10 января 2012

Как насчет

Debug.Print(Test.ToString().Split("."c)(0))

У меня не было никаких краевых случаев, но это сработало на нескольких примерах, которые я пробовал. Я не рекомендовал бы это решение, если это нужно будет выполнять в цикле, поскольку оно не будет работать хорошо, но это может быть пробел, пока вы не найдете что-то лучшее.

1 голос
/ 10 января 2012

Другой подход, совершенно другой. Поскольку проблема, похоже, связана с двойными числами и преобразованиями, мы могли бы избежать двойных операций, делающих только вычитания:

Dim Start As Integer = 0
Dim [End] As Integer = 255
Dim Increment As Integer = 3
Dim Current as Integer = Start

While Current < End
    Current = Current + Increment
    LedR.SetPulse(255, CType(Current ,UInteger))
    Threading.Thread.Sleep(20)
End While

Quick & Dirty, но это работает.

1 голос
/ 10 января 2012

Что бы ни происходило, я бы посоветовал вам избегать UInts столько, сколько вы можете (я был там). Я бы написал код так:

Dim Start As Integer = 0
Dim [End] As Integer = 255
Dim Steps As Integer = 100

For x As Integer = 1 To Steps
    Dim Temp As Integer = ([End] - Start) \ Steps * x + Start
    LedR.SetPulse(255, CType(Temp,UInteger))
    Threading.Thread.Sleep(20)
Next

Я не могу попробовать это, потому что у меня нет доступного компилятора Vb.Net, и я написал код непосредственно на SO, пожалуйста, прости меня, если есть какие-либо ошибки компиляции.

...