Showing posts with label one. Show all posts
Showing posts with label one. Show all posts

Tuesday, July 31, 2012

Small Basic Programming Challenge#1


'Programming Challenge#1
'Microsoft Small Basic
'Harry Hardjono
'July 2012
'

text1="I'm singing in the rain!"
text2="The quick brown fox jumps over the lazy dog."
text3="a SMALL misfortune"

t1="abcdefghijklmnopqrstuvwxyz"
t2="ABCDEFGHIJKLMNOPQRSTUVWXYZ"

Tin=text1
UpperLower()
Tin=text2
UpperLower()
Tin=text3
UpperLower()

Tin1=text3
Tin2=text2
Cin="SMALL"
CharIndex()
If Cout="" then
TextWindow.WriteLine("Not found!")
else
TextWindow.WriteLine(Cout)
endif

Tin1=text3
Tin2=text2
Cin="Small"
CharIndex()
If Cout="" then
TextWindow.WriteLine("Not found!")
else
TextWindow.WriteLine(Cout)
endif

Tin=text1
MakeAlpha()
TextWindow.WriteLine(Tout)
Tin=text2
MakeAlpha()
TextWindow.WriteLine(Tout)
Tin=text3
MakeAlpha()
TextWindow.WriteLine(Tout)

Tin=text1
IsPangram()
TextWindow.WriteLine(Tout)
Tin=text2
IsPangram()
TextWindow.WriteLine(Tout)
Tin=text3
IsPangram()
TextWindow.WriteLine(Tout)


Tin1=text1
Tin2="AEIOU"
StringOut()
TextWindow.WriteLine(Tout)
Tin1=text2
Tin2="aeiou"
StringOut()
TextWindow.WriteLine(Tout)
Tin1=text3
Tin2="qwrtypsdfghjklzxcvbmn"
StringOut()
TextWindow.WriteLine(Tout)


Filename=Program.Directory+"\hangman.txt"
FileSlurp()
For i=1 To Array.GetItemCount(FileData)
TextWindow.WriteLine(FileData[i])
endfor

Sub FileSlurp
'Read a file and assign it to an array
'Input Filename (string)
'Output FileData (array)
FileLength=Text.GetLength(File.ReadContents(Filename))
FileData=""
FL=0
FS_i=1
While FL < filelength
  FileData[FS_i]=File.ReadLine(Filename,FS_i)
  FL=FL+Text.GetLength(FileData[FS_i])+2
  If FileData[FS_i]="" Then 'Fudge for blank lines in file
    FileData[FS_i]=" "
  EndIf
  FS_i=FS_i+1
Endwhile
EndSub



Sub UpperLower
TextWindow.WriteLine(Tin)
Text_Lower()
TextWindow.WriteLine(Tout)
Text_Upper()
TextWindow.WriteLine(Tout)
EndSub


Sub Text_Lower
  'Make Tin string lowercase
  'Input Tin (string)
  'Output Tout (string)
  Tout=""
  For TL_i=1 To Text.GetLength(Tin)
    tchar=text.GetSubText(Tin,TL_i,1)
    tindx=text.GetIndexOf(t2,tchar)
    If tindx>0 Then
      tchar=text.GetSubText(t1,tindx,1)
    EndIf
    Tout=Text.Append(Tout,tchar)
  EndFor
EndSub


Sub Text_Upper
  'Make Tin string uppercase
  'Input Tin (string)
  'Output Tout (string)
  Tout=""
  For TL_i=1 To Text.GetLength(Tin)
    tchar=text.GetSubText(Tin,TL_i,1)
    tindx=text.GetIndexOf(t1,tchar)
    If tindx>0 Then
      tchar=text.GetSubText(t2,tindx,1)
    EndIf
    Tout=Text.Append(Tout,tchar)
  EndFor
EndSub

Sub CharIndex
  'Given 2 strings and a char, find the corresponding char from location t1 at t2
  'return "" if not found. return char/string otherwise
  'Input Tin1 = in index string
  'Input Tin2 = out index string
  'Input Cin = character / string
  'Output Cout = character/string
  tindx=text.GetIndexOf(Tin1,Cin)
  If (tindx=0) Then
    Cout=""
  Else
    Cout=text.GetSubText(Tin2,tindx,text.GetLength(Cin))
  EndIf
EndSub

Sub MakeAlpha
  'Given a string, pick out all alphabet. Store in UPPERCASE
  'Input Tin = string (text)
  'Output Tout = string (alphabets)
  Tout=""
  For MA_i = 1 To Text.GetLength(Tin)
    tchar=text.ConvertToUpperCase(text.GetSubText(Tin,MA_i,1))
    tindx=text.GetIndexOf(t2,tchar)
    If tindx>0 Then
      tindx=text.GetIndexOf(Tout,tchar)
      If tindx=0 Then
        Tout=Text.Append(Tout,tchar)
      EndIf
    EndIf
  EndFor
EndSub


Sub IsPangram
  'Given a string, see if all alphabets is represented
  'Input Tin = string(text)
  'Output Tout = string "TRUE" if yes. "FALSE" if false
  Tin1=text.ConvertToUpperCase(Tin)
  Tout="TRUE"
  For IP_i=1 To Text.GetLength(t2)
    tchar=Text.GetSubText(t2,IP_i,1)
    tindx=text.GetIndexOf(Tin1,tchar)
    If (tindx=0) Then
      Tout="FALSE"
    EndIf
  EndFor
EndSub

Sub CharOut
  'Given 2 strings return string of char found in Tin1, but not in Tin2
  'return string
  'Note: No character upper/lower conversion is done.
  'Input Tin1 = main index string
  'Input Tin2 = sub index string
  'Output Tout = character/string
  Tout=""
  For CO_i=1 To Text.GetLength(Tin1)
    tchar=text.GetSubText(Tin1,CO_i,1)
    tindx=text.GetIndexOf(Tin2,tchar)
    If (tindx=0) Then
      Tout=Text.Append(Tout,tchar)
    EndIf
  EndFor
EndSub

Sub StringOut
  'Given 2 strings return string of char found in Tin1, but not in Tin2
  'return string
  'Note: Convert all char to UPPER
  'Note: Calls CharOut(), MakeAlpha()
  'Input Tin1 = main index string
  'Input Tin2 = sub index string
  'Output Tout = character/string
 
  Tin1=text.ConvertToUpperCase(Tin1)
  Tin2=text.ConvertToUpperCase(Tin2)
  CharOut()
  Tin=Tout
  MakeAlpha()
EndSub

Tuesday, May 15, 2012

Small Basic Converter Code

One of April challenges is writing a converter, the kind that converts meter to yard. A lot of people are doing it the hard coding way. I am way to busy to do that. So, I decided to spend one hour on it, and no more! The result is here. Not perfect, but close enough.

There are several design issues:
1. The display for various conversion and the result is rolled into one.
2. You only select the original data, all the possible conversions is done automatically.
3. Range is limited to valid input
4. The data is provided via text. You can modify the text to suit.
5. More importantly, the text also include range of numbers, which the program uses for conversion. The ratio for conversion is calculated automatically. This includes negative numbers, or shifting numbers (i.e. 1-5 into 3-7)
6. I use a hidden Main scale to facilitate ease of conversion.
7. Pay attention to Field[] entries! They defined the data field locations!

These design decisions helped me contained the implementation of this program into one hour.

I did encounter one bug. When copying Choice Loop into NumLoop, I forgot to change the Goto statement, so it went back to Choice Loop. Easily fixed.

Turns out, the algorithm for conversion is robust enough to handle out of range condition, so that I don't have to restrict its input. I could have avoided that bug after all.

It also means, that I don't have to show the range of numbers. It means I can just display the descriptions, and the converted numbers. It would make a cleaner presentation.


'Small Basic Converter - ZLW480
'By Harry Hardjono
'April 2012
'
Init:
MainMin=0
MainNum=0
MainMax=9999999

Field[1]=1 'N
Field[2]=3 'Description
Field[3]=14 'From
Field[4]=18 'Min
Field[5]=28 'To
Field[6]=30 'Max
Field[7]=40 ':

'Data[0]="N DescriptionFrom To :"
Data[1]="1 USD From 0 To 100000 : "
Data[2]="2 GBP From 0 To 158308 : "
Data[3]="3 CAD From 0 To 99962 : "
Data[4]="4 EUR From 0 To 130240 : "
Data[5]="5 AUD From 0 To 103447 : "

TextWindow.WriteLine("Small Basic Converter")

MainLoop:
For i=1 To Array.GetItemCount(Data)
TextWindow.Write(Text.GetSubText(Data[i],1,Text.GetLength(Data[i])))
mx1=MainMin
mx2=MainNum
mx3=MainMax
my1=Text.GetSubText(Data[i],Field[4],Field[5]-Field[4])
my3=Text.GetSubText(Data[i],Field[6],Field[7]-Field[6])
map()
TextWindow.WriteLine(my2)
EndFor
TextWindow.WriteLine(" ")
ChoiceLoop:
TextWindow.Write(("Which data(1-"+Array.GetItemCount(Data))+")?")
Choice=TextWindow.ReadNumber()
If (Choice<1 or Choice>Array.GetItemCount(Data)) then
TextWindow.WriteLine("Out of Range!")
Goto ChoiceLoop
endif
NumLoop:
TextWindow.WriteLine(Text.GetSubText(Data[Choice],Field[4],Field[5]-Field[4])+" to "+Text.GetSubText(Data[Choice],Field[6],Field[7]-Field[6]))
TextWindow.Write("Enter the amount: ")
Num=TextWindow.ReadNumber()
' If (NumText.GetSubText(Data[Choice],Field[6],Field[7]-Field[6])) then
' TextWindow.WriteLine("Out of Range!")
' Goto NumLoop
'endif

mx1=Text.GetSubText(Data[Choice],Field[4],Field[5]-Field[4])
mx2=Num
mx3=Text.GetSubText(Data[Choice],Field[6],Field[7]-Field[6])
my1=MainMin
my3=MainMax
map()
MainNum=my2

Goto MainLoop
Sub map 'map function
'x1-x2-x3 y1-y2-y3
my2=((my3-my1)*(mx2-mx1)/(mx3-mx1))+my1
EndSub

Tuesday, May 8, 2012

Small Basic Morse Code

I got bored one day, and hey, remember that Rock/Paper/Scissors game? That was quick. So I was hunting for a quick coding project, quicker than my usual one hour session. The Morse code is it. It took about 10 minutes, including typing all those entries. Of course, the original design was phonetic alphabet project, but I decided that typing Morse code entries would be faster than typing phonetic alphabet entries.

BTW, you don't have to limit yourself. You can do your own project like this, and substitute Klingon alphabet, for example. Do you know that Small Basic uses Unicode? Try looping some big numbers through Text.GetCharacter and you'll get the idea.

Of course, as luck would have it, I still have some time, so I improved it with tones. I think there is something wrong here because the sound is so soft! Oh, well.

'Extending the code, as well as decoding is left as an exercise for the reader!
Morse="a=+-;b=-+++;c=-+-+;d=-++;e=+;f=++-+;g=--+;h=++++;i=++;j=+---;k=-+-;l=+-++;m=--;n=-+;o=---;p=+--+;q=--+-;r=+-+;s=+++;t=-;u=++-;v=+++-;w=+--;x=-++-;y=-+--;z=--++;"
Loop:
TextWindow.Write("Enter Text:")
t=TextWindow.Read()
For i=1 To Text.GetLength(t)
TextWindow.Write((Morse[Text.ConvertToLowerCase(Text.GetSubText(t,i,1))])+" ")
EndFor
TextWindow.WriteLine(" ")
Goto Loop


'Extending the code, as well as decoding is left as an exercise for the reader!
Morse="a=+-;b=-+++;c=-+-+;d=-++;e=+;f=++-+;g=--+;h=++++;i=++;j=+---;k=-+-;l=+-++;m=--;n=-+;o=---;p=+--+;q=--+-;r=+-+;s=+++;t=-;u=++-;v=+++-;w=+--;x=-++-;y=-+--;z=--++;"
TextWindow.WriteLine("Morse Code Encoder by Harry Hardjono")
Loop:
TextWindow.Write(Text.GetCharacter(13)+Text.GetCharacter(10)+"Enter Text:")
t=TextWindow.Read()
For i=1 To Text.GetLength(t)
MC=Text.Append(MC,(Morse[Text.ConvertToLowerCase(Text.GetSubText(t,i,1))]+" ")) 'Comment this out for no sound
TextWindow.Write((Morse[Text.ConvertToLowerCase(Text.GetSubText(t,i,1))])+" ")
EndFor
PlayMorse() 'Comment this out for no sound
Goto Loop

Sub PlayMorse
TT="+=C12;-=C4; =P4;"
For j=1 To Text.GetLength(MC)
MT=Text.Append(MT,TT[Text.GetSubText(MC,j,1)])
EndFor
Sound.PlayMusic(MT)
MC=""
MT=""
EndSub