自然言語ライブラリの用法 — プログラミング言語 Ring 1.14 取扱説明書

Skip to content

# 自然言語ライブラリの用法

自然言語ライブラリで命令グループのある言語を手軽に定義するための用法です。

自然言語ライブラリの使用前に naturallib.ring ライブラリを読み込みます。

    load "naturallib.ring"

ライブラリの読み込み後、このメソッドで自然言語を使えます。

- SetLanguageName(cLanguageName)

- setCommandsPath(cFolder)

- SetPackageName(cPackageName)

- UseCommand(cCommandName)

- SetOperators(cOperators)

- RunFile(cFileName)

- RunString(cString)

## 自然言語ライブラリ - デモプログラム

例えば、テキストファイル program.txt に自然言語コードを記述します。

ファイル: program.txt

    Welcome to the Ring programming language!
    What you are reading now is not comments, I swear!

    After many years of programming I decided to think different about
    programming and solve the problems in a better way.

    We are writing commands or code and the Ring language is reading
    it to understand us! Sure, What you are seeing now is
    just ***part of the code - Not the Complete Program***
    You have to write little things before and after this
    part to be able to run it!

    It is the natural part of our code where we can write in English,
    Arabic or any Natural Language Then we will tell the computer
    through the Ring language what must happens! in a way that we can scale
    for large frameworks and programs.

    Just imagine what will happens to the world of programming once
    we create many powerful frameworks using the Ring language that
    uses this way (Natural Programming).

    For example When we say Hello to the Machine, It can reply! and when we
    say count from 1 to 5 it will understand us, Also if
    we said count from 5 to 1 it will
    understand us too! You can see the Output window!

    This Goal is not new, but the Ring language comes
    with an innovative solution to this problem.

実行結果:

    Hello, Sir!

    The Numbers!

    1

    2

    3

    4

    5

    I will count Again!

    5

    4

    3

    2

    1

自然言語コードを実行するには start.ring が必要です。

start.ring には言語と命令を定義します。

ファイル: start.ring

    load "stdlib.ring"
    load "naturallib.ring"

    New NaturalLanguage {
            SetLanguageName(:MyLanguage)
            SetCommandsPath(CurrentDir()+"/../command")
            SetPackageName("MyLanguage.Natural")
            UseCommand(:Hello)
            UseCommand(:Count)
            RunFile("program.txt")
    }

これで MyLanguage 言語名は定義済みになり、言語命令用のフォルダが指定されます。

各命令は MyLanguage.Natural パッケージにあるクラスとして定義されています。

Hello と Count の二つの命令を定義しています。

CurrentDir()+”/../command” フォルダで命令を定義するために二つのファイルが必要です。

ファイル: hello.ring

    DefineNaturalCommand.SyntaxIsKeyword([
            :Package = "MyLanguage.Natural",
            :Keyword = :hello,
            :Function = func {
                    See  "Hello, Sir!" + nl + nl
            }
    ])

ファイル: count.ring

    DefineNaturalCommand.SyntaxIsKeywordNumberNumber([
            :Package = "MyLanguage.Natural",
            :Keyword = :count,
            :Function = func {
                    if not isattribute(self,:count_times) {
                            AddAttribute(self,:count_times)
                            Count_Times = 0
                    }
                    if Expr(1) > Expr(2) {
                            nStep = -1
                    else
                            nStep = 1
                    }
                    if Count_Times = 0 {
                            see nl+"The Numbers!" + nl
                            Count_Times++
                    else
                            see nl + "I will count Again!" +nl
                    }
                    for x = Expr(1) to Expr(2) step nStep {
                            see nl+x+nl
                    }
                    CommandReturn(fabs(Expr(1)-Expr(2))+1)
            }
    ])

## 命令の定義

DefineNaturalCommand オブジェクトで新しい命令を定義します。

このオブジェクトでは、下記のメソッドが使えます。

- SyntaxIsKeyword(aPara)

- SyntaxIsKeywordNumber(aPara)

- SyntaxIsKeywordNumberNumber(aPara)

- SyntaxIsKeywordNumbers(aPara,nCount)

- SyntaxIsKeywordString(aPara)

- SyntaxIsKeywordStringString(aPara)

- SyntaxIsKeywordStrings(aPara,nCount)

- SyntaxIsKeywordExpression(aPara)

- SyntaxIsKeywordExpressionExpression(aPara)

- SyntaxIsKeywordExpressions(aPara,nCount)

- SyntaxIsCommand(aPara)

- SyntaxIsCommandNumber(aPara)

- SyntaxIsCommandNumberNumber(aPara)

- SyntaxIsCommandNumbers(aPara,nCount)

- SyntaxIsCommandString(aPara)

- SyntaxIsCommandStringString(aPara)

- SyntaxIsCommandStrings(aPara,nCount)

- SyntaxIsCommandExpression(aPara)

- SyntaxIsCommandExpressionExpression(aPara)

- SyntaxIsCommandExpressions(aPara,nCount)

ファイル: mylanguage.ring

    load "stdlib.ring"
    load "naturallib.ring"

    MyLanguage = New NaturalLanguage {
            SetLanguageName(:MyLanguage)
            SetCommandsPath(CurrentDir()+"/../command")
            SetPackageName("MyLanguage.Natural")
            UseCommand(:Hello)
            UseCommand(:Count)
            UseCommand(:Print)
            UseCommand(:IWantWindow)
            UseCommand(:WindowTitleIs)
            UseCommand(:IWantButton)
    }

用例①

この用例では、 Print 命令を定義します。

SyntaxIsKeywordExpression() メソッドを使用します。

メソッドにはリスト (ハッシュとして) を渡します。 実行するパッケージ名、キーワード、および関数を決定します。

この定義にある Expr(nExprNumber) 関数はユーザがキーワードの後に記述する式の値を取得します。

ファイル: print.ring

    DefineNaturalCommand.SyntaxIsKeywordExpression([
            :Package = "MyLanguage.Natural",
            :Keyword = :print,
            :Function = func {
                    See  Expr(1)
            }
    ])

用法:

    load "mylanguage.ring"

    MyLanguage.RunString('
            print "Hello, World!"
    ')

実行結果:

    Hello, World!

用例②

ファイル: iwantwindow.ring

    DefineNaturalCommand.SyntaxIsCommand([
            :Package = "MyLanguage.Natural",
            :Command = "i want window",
            :Function = func {
                    See  "Command: I want window" + nl
            }
    ])

用法:

    load "mylanguage.ring"

    MyLanguage.RunString('
            i want window
    ')

実行結果:

    Command: I want window

用例③

ファイル: windowtitleis.ring

    DefineNaturalCommand.SyntaxIsCommandString([
            :Package = "MyLanguage.Natural",
            :Command = "window title is",
            :Function = func {
                    See  "Command: Window title is " + Expr(1) + nl
            }
    ])

用法:

    load "mylanguage.ring"

    MyLanguage.RunString('
            I want window and the window title is "Hello World"
    ')

実行結果:

    Command: I want window
    Command: Window title is Hello World

## 自然言語ライブラリ - 演算子

この用例は演算子ではなく Count 命令を使用しています。

    load "mylanguage.ring"

    MyLanguage.RunString("
            Hello
            Count 1 5
            Count 5 1
    ")

詳述すると、

    load "mylanguage.ring"

    MyLanguage.RunString("
            Hello, Please   Count from 1 to 5 then count from 5 to 1
    ")

また、命令は “(” や ”)” などの演算子で囲むことができます。

    load "mylanguage.ring"

    MyLanguage {
            SetOperators("()")
            RunString("
                    Here we will play and will try something
                    that looks like Lisp Syntax
                    (count  (count 1 5)  (count 20 15))
                    Just for fun!
            ")
    }

## クラスによる命令の定義

実装について詳しく説明します。

自然言語ライブラリは新規命令の定義をするたびにクラスを定義します。

DefineNaturalCommand オブジェクト、またはこの用例のように、新しいクラスの定義により単純明快なインタフェースで命令を定義する選択肢があります。

DefineNaturalCommand (最も簡単な方法) は実行時にクラスを定義します。

ファイル: hello.ring

    Package MyLanguage.Natural

    class Hello

            func AddAttributes_Hello
                    AddAttribute(self,:hello)

            func GetHello
                    See  "Hello, Sir!" + nl + nl

ファイル: count.ring

    Package MyLanguage.Natural

    class Count

            func Getcount
                    StartCommand()
                    CommandData()[:name] = :Count
                    CommandData()[:nExpr] = 0
                    CommandData()[:aExpr] = []

            func BraceExprEval_Count nValue
                    if isCommand() and CommandData()[:name] = :Count {
                            if isNumber(nValue) {
                                    CommandData()[:nExpr]++
                                    CommandData()[:aExpr] + nValue
                                    if CommandData()[:nExpr] = 2 {
                                            Count_Execute()
                                    }
                            }
                    }

            func AddAttributes_Count
                    AddAttribute(self,:count)

            func Count_Execute
                    if not isattribute(self,:count_times) {
                            AddAttribute(self,:count_times)
                            Count_Times = 0
                    }
                    if Expr(1) > Expr(2) {
                            nStep = -1
                    else
                            nStep = 1
                    }
                    if Count_Times = 0 {
                            see nl+"The Numbers!" + nl
                            Count_Times++
                    else
                            see nl + "I will count Again!" +nl
                    }
                    for x = Expr(1) to Expr(2) step nStep {
                            see nl+x+nl
                    }
                    CommandReturn(fabs(Expr(1)-Expr(2))+1)