2010年1月26日 星期二

2010/01/26 字串內容

請設計一程式,讀取"in.txt"中A、B兩字串(A長度小於B),並判斷字串A中之所有字元是否依序(不要求相鄰)出現在字串B中(大小寫不分)。

輸入範例:

A=dos
B=Doctor of philosophy

輸出範例:

輸出答案為  是

出自  程式設計隊訓練教材  NO.18  字串內容

21 則留言:

  1. 似乎一天一題,大家進度也沒跟上嗎?
    還是隊員們習慣到學校去,一塊兒討論嗎?
    先努力過這個寒假,開學了,一同討論的時間就會多了吧?
    加油。

    回覆刪除
  2. Private Sub Form_Load()
    Dim a(20) As String
    Dim b(50) As String
    Dim ans As Boolean
    ans = True
    Open App.Path & "\in.txt" For Input As #1
    Input #1, x
    x = Right(x, Len(x) - 2)
    x = LCase(x)
    Input #1, y
    y = Right(y, Len(y) - 2)
    y = LCase(y)
    Close #1
    If Len(x) > Len(y) Then
    ans = False
    End If
    k1 = 0
    k2 = 0
    Do Until y = ""
    b(k2 + 1) = Mid(y, 1, 1)
    y = Right(y, Len(y) - 1)

    k2 = k2 + 1
    Loop
    Do Until x = ""
    a(k1 + 1) = Mid(x, 1, 1)
    x = Right(x, Len(x) - 1)
    k1 = k1 + 1
    Loop
    n1 = 0
    For i = 1 To k2
    If a(n1 + 1) = b(i) Then
    n1 = n1 + 1
    i = 1
    End If
    Next i
    If n1 = k1 Then
    Else
    ans = False
    End If
    Open App.Path & "\out.txt" For Output As #1
    If ans Then
    Print #1, "是"
    Else
    Print #1, "不是"
    End If

    Close #1
    End Sub

    回覆刪除
  3. 老師 你是覺得以後要返校嗎=O=?

    回覆刪除
  4. Dim a(999) As String
    Dim b(999) As String
    Private Sub Form_Load()

    Open App.Path & "\in.txt" For Input As #1
    Input #1, a1, b1
    Close #1

    n = Len(a1)
    m = Len(b1)

    X1 = 1
    X2 = 1

    For i = 1 To n
    x = Mid(a1, i, 1)
    If ax <> " " Then
    a(X1) = LCase(x)
    X1 = X1 + 1
    End If
    Next i

    For j = 1 To m
    y = Mid(b1, j, 1)
    If y <> " " Then
    b(X2) = LCase(y)
    X2 = X2 + 1
    End If
    Next j

    k = 1
    h = 0

    For i = 1 To X1
    q1 = False
    For j = k To X2
    If a(i) = b(j) Then
    q1 = True
    k = j + 1
    Exit For
    End If
    Next j
    If q1 = False Then
    ans = True
    Exit For
    End If
    Next i

    If q1 = False Then
    ans = False
    End If


    Open App.Path & "\out.txt" For Output As #2
    If ans Then
    Print #2, "輸出答案為 是"
    Else
    Print #2, "輸出答案為 不是"
    End If
    Close #2
    End Sub

    回覆刪除
  5. 有考慮過用"Split"這個函數來做
    但是我做的時候會溢位,希望老師可以在指點一下=ˇ=

    回覆刪除
  6. Y揚好,
    1.你的程式似乎有錯吧?題目有要求要「依序」雖然不必相鄰。
    若A=sod
    B=Doctor of philosophy
    你的程式的答案還是「是」吧?
    2.雖然是想大家回學校,不過,我的旅行要到2/7才回到台灣,而2/9就是返校日了。
    3.你的程式,「i=1」這行多了吧?

    回覆刪除
  7. 阿瑋好,
    1.x = Mid(a1, i, 1)
    If ax <> " " Then
    這個ax是錯字吧?
    2.雖然想法還是有些怪,似乎程式是可以的。
    3.你們兩人的輸入和輸出不一樣,是誰的問題呢?
    隊長,輸入的寫法,和輸出的寫法,要再更確定些。
    例如:
    假設 in.txt 的內容是:
    dos
    Doctor of philosophy
    則輸出的out.txt的內容是:

    4.用split的話,用空白來分也不錯,用逗號來分,又沒有逗號,所以並不適合。而且,以比賽來說,少用各種複雜的函數是基本的要求。
    以這題來講,連Lcase這個函數可能都要自己做哦。
    要不然,乾脆連inStr這個函數都拿來用,不就更快了。將短的那個字,拆開後,去用inStr找到是不是所有的字都在長的那個字裡找得到,而且是找到的位置越來越大。

    回覆刪除
  8. Y揚、阿瑋好,
    你們兩人的程式,Y揚的方式比較好,只是,你們兩個都用了陣列去拆字串,何必呢?
    反正拆了也沒有要做什麼,何不只用兩個變數來記住位置就好了呢?

    回覆刪除
  9. 我忘記做到依序=ˋ=
    我原本是做
    A=Doctor
    B=Doctor of philosophy
    只要B 有A的全部"字母" 答案 就是
    我沒有做到排序
    I=1 是因為確定找到1個之後重新找第2個字母

    回覆刪除
  10. 改好了 =) 2個變數是?
    Private Sub Form_Load()
    Dim ans As Boolean
    ans = True
    Open App.Path & "\in.txt" For Input As #1
    Input #1, x
    x = Right(x, Len(x) - 2)
    x = LCase(x)
    Input #1, y
    y = Right(y, Len(y) - 2)
    y = LCase(y)
    Close #1
    If Len(x) > Len(y) Then
    ans = False
    End If
    For i = 1 To Len(y)
    X1 = Left(x, 1)
    X2 = Left(y, 1)
    If X1 = X2 Then
    x = Right(x, Len(x) - 1)
    End If
    y = Right(y, Len(y) - 1)
    Next i
    Open App.Path & "\out.txt" For Output As #1
    If x = "" Then
    Print #1, "是"
    Else
    Print #1, "不是"
    End If
    Close #1
    End Sub

    回覆刪除
  11. Private Sub Form_Load()
    Open App.Path & "/in.txt" For Input As #1
    Input #1, x, y
    a = Right(x, Len(x) - 2)
    b = Right(y, Len(y) - 2)
    isTrue = True
    Apoint = 1
    Bpoint = 1
    For i = 1 To Len(a)
    t = Mid(a, i, 1)
    For j = Bpoint To Len(b)
    w = Mid(b, j, 1)
    If t = w Then Bpoint = j: Apoint = i: Exit For
    Next j
    Next i
    Open App.Path & "/out.txt" For Output As #2
    If Apoint <> Len(a) Then
    Print #2, "否"
    Else
    Print #2, "是"
    End If
    Close #2
    Close #1
    End Sub
    我這個 自己測試了一下"yos",答案為"否"
    有點奇怪的地方是 我沒設定判斷大小寫的
    可是 程式裡面好像判定D跟d是一樣的
    所以 我的dos答案為"是"
    這點不清楚為何會這樣說

    回覆刪除
  12. Y揚好,
    你的程式應該可以的,兩個變數只是我的講法,反正就是記住x,y的地方而已。你用了x本身來記x,用迴圈
    for i = 1 to len(y)
    來記住y,OK的啦。

    回覆刪除
  13. 高仔好,
    你的程式會有問題的吧,不只"dos" "Dos"會可以,"Mos","Bos"也會可以的吧,因為如果你前面的字都沒找到,Apoint和Bpoint也不會變的,而反而還是會
    for i = 1 to len(n)
    t = mid(a,i,1)
    這個地方還是會前進,於是除非是第一個字有找到,不然是沒影響的。

    回覆刪除
  14. 高仔,y揚好,
    只是,
    你們兩個的讀入檔還是不同吧?你們去試試對方的in.txt檔,會得到不同的答案吧。
    還有,高仔,你用
    input #1,x,y
    一次讀入兩個字串,確定可以嗎? 讀進來之後,有用print 之類方式,將它給顯示出來過嗎?

    回覆刪除
  15. 嗯嗯 我的程式碼錯誤很嚴重
    還在試著用原本的思路改進
    有點卡住
    至於input #1,x,y
    我有用print確認
    顯示出來並無錯誤

    回覆刪除
  16. Private Sub Form_Load()
    Open App.Path & "/in.txt" For Input As #1
    Input #1, x, y
    a = LCase(Right(x, Len(x) - 2))
    b = LCase(Right(y, Len(y) - 2))
    isTrue = True
    Apoint = 0
    For i = 1 To Len(a)
    t = Mid(a, i, 1)
    For j = 1 To Len(b)
    w = Mid(b, j, 1)
    If t = w Then b = Right(b, Len(b) - j): j = 0: Apoint = i: Exit For
    If j = Len(b) And Apoint <> Len(a) Then isTrue = False
    Next j
    Next i
    Open App.Path & "/out.txt" For Output As #2
    If isTrue = False Then
    Print #2, "否"
    Else
    Print #2, "是"
    End If
    Close #2
    Close #1
    End Sub
    基本上跟上次所發的一樣
    變動的地方是 找到指定字元過後刪除b前段的字元
    以及大小寫的統一
    比較偷懶的用了內定函數
    不過大小寫的轉換若不用Lcase 倒是有想到 使用Asc求出文字內碼配合阿緯在"年曆轉換"中使用的方式
    只是不知道這樣是否算違規
    因為Asc也算是內定函數

    回覆刪除
  17. 高仔好,
    1.這次的程式,應該是OK的。
    2.通常如果限定使用函數的場合,一些必要的函數還是會被列舉出來的。
    我想,像asc這樣查表的函數是可以的。

    回覆刪除
  18. Dim a(50) As String
    Dim b(50) As String
    Dim ansR(50) As Integer

    Private Sub Form_Load()
    Open App.Path & "\in.txt" For Input As #1
    Open App.Path & "\out.txt" For Output As #2
    Input #1, Ast
    Input #1, Bst
    MaxA = Len(Ast) - 2
    maxB = Len(Bst) - 2
    For i = 1 To 50
    ansR(i) = 0
    Next i
    For i = 1 To MaxA
    a(i) = Mid(Ast, i + 2, 1)
    a(i) = LCase(a(i))
    Next i
    For i = 1 To maxB
    b(i) = Mid(Bst, i + 2, 1)
    b(i) = LCase(b(i))
    Next i


    c = 1
    Do Until c = MaxA + 1
    For i = 1 To maxB
    If a(c) = b(i) Then
    ansR(c) = i
    Exit For
    End If
    Next i
    c = c + 1
    Loop
    ans = False
    d = 1
    Do
    If ansR(d) < ansR(d + 1) Then ans = True
    If ansR(d + 1) = 0 Then
    ans = False
    Exit Do
    End If
    d = d + 1
    Loop Until d = MaxA

    If ans = False Then
    Print#2, "否"
    Else
    Print#2, "是"
    End If

    Close #2
    Close #1
    End Sub

    回覆刪除
  19. 小白好,
    這一段程式會出錯吧。

    Do
    If ansR(d) < ansR(d + 1) Then ans = True
    If ansR(d + 1) = 0 Then
    ans = False
    Exit Do
    End If
    d = d + 1
    Loop Until d = MaxA

    你有的狀況設為true,又有狀況設為 false,
    來來去去的,如果要找的字串很常,那麼就可能在真真假假中,直到最後一個。
    錯。

    回覆刪除
  20. 其實這題不用很多判斷式
    用裁切的方式就可以做完
    一個迴圈,幾行程式碼就可以了
    將字串切掉

    回覆刪除
  21. Public Sub Form_Load()
    Me.Hide
    Open App.Path & "/in.txt" For Input As #1
    Open App.Path & "/out.txt" For Output As #2
    Line Input #1, x
    Line Input #1, y
    x = LCase(Right(x, Len(x) - 2))
    y = LCase(Right(y, Len(y) - 2))
    m = 0
    For i = 1 To Len(x)
    If InStr(y, Mid(x, i, 1)) > m Then
    m = InStr(y, Mid(x, i, 1))
    Else
    Print #2, "否": Exit Sub
    End If
    Next i
    Print #2, "是"
    Close #2
    Close #1
    End
    End Sub

    5分

    回覆刪除