递增序言中的计数器

发布于 2025-01-26 06:16:23 字数 964 浏览 5 评论 0原文

这是我正在处理的问题的当前代码。它应该从文件中读取,并每次遇到元音时,将计数器(r)添加。 目前,我在到达元音时停止了,但是我希望它增加计数器,然后继续处理。完成后,我希望它将R打印到控制台。提前致谢!

readWord(InStream, W) :-
        get0(InStream,Char),
        checkChar_readRest(Char,Chars,InStream, R),
        atom_codes(Code,Chars),
        write(Code).

%checkChar_readRest(10,[],_) :- !. % Return
%checkChar_readRest(32,[],_) :- !. % Space
checkChar_readRest(-1,[],_,_) :- !. % End of Stream
checkChar_readRest(97,[],_,R) :- !. % a
checkChar_readRest(101,[],_,R) :- !. % e
checkChar_readRest(105,[],_,R) :- !. % i
checkChar_readRest(111,[],_,R) :- incr(R,R1), write(R1). % o
checkChar_readRest(117,[],_,R) :- !. % u
%checkChar_readRest(end_of_file,[],_,_) :- !.
checkChar_readRest(Char,[Char|Chars],InStream,R) :-
    get0(InStream,NextChar),
    checkChar_readRest(NextChar,Chars,InStream,R).

incr(X, X1) :- X1 is X+1.

vowel(InStream, R) :- 
    open(InStream, read, In), 
    repeat,
    readWord(In, W),
    close(In).

This is the current code I have for a problem I am working on. It is supposed to read in from a file, and increment a counter, R, every time it comes across a vowel.
Currently, I have it stop when reaching a vowel, but I would like it to increment a counter, then continue processing. Once done, I want it to print R to the console. Thanks in advance!

readWord(InStream, W) :-
        get0(InStream,Char),
        checkChar_readRest(Char,Chars,InStream, R),
        atom_codes(Code,Chars),
        write(Code).

%checkChar_readRest(10,[],_) :- !. % Return
%checkChar_readRest(32,[],_) :- !. % Space
checkChar_readRest(-1,[],_,_) :- !. % End of Stream
checkChar_readRest(97,[],_,R) :- !. % a
checkChar_readRest(101,[],_,R) :- !. % e
checkChar_readRest(105,[],_,R) :- !. % i
checkChar_readRest(111,[],_,R) :- incr(R,R1), write(R1). % o
checkChar_readRest(117,[],_,R) :- !. % u
%checkChar_readRest(end_of_file,[],_,_) :- !.
checkChar_readRest(Char,[Char|Chars],InStream,R) :-
    get0(InStream,NextChar),
    checkChar_readRest(NextChar,Chars,InStream,R).

incr(X, X1) :- X1 is X+1.

vowel(InStream, R) :- 
    open(InStream, read, In), 
    repeat,
    readWord(In, W),
    close(In).

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(2

挽心 2025-02-02 06:16:23

这是我的尝试(ISO谓词):

% open Src, count vowels, close stream, print to console
count_vowels_in(Src) :-
    open(Src, read, Stream),
    count(Stream, Total),
    close(Stream),
    % cutting here because our Stream is now closed, any backtracking will break things that rely on it
    % you could also put this after at_end_of_stream/1 in count_/3
    % not sure what best practices are here
    !,
    write(Total).

% just a nice wrapper to get started counting with the initial count set to 0
count(Stream, Total) :-
    count_(Stream, 0, Total).

% at end of stream, Count = Total and we're done
count_(Stream, Count, Count) :-
    at_end_of_stream(Stream).

% read from stream recursively, incrementing Count as needed
count_(Stream, Count0, Total) :-
    \+at_end_of_stream(Stream),
    get_char(Stream, Char),
    char_value(Char, Value),
    Count1 is Count0 + Value,
    % recursively call count_, but now with our new Count1 value instead, carrying forward the results
    count_(Stream, Count1, Total).

char_value(Char, 1) :-
    vowel(Char).
char_value(Char, 0) :-
    \+vowel(Char).

vowel(a).
vowel(e).
vowel(i).
vowel(o).
vowel(u).

最大的区别是我使用两个变量来跟踪计数。 count(等效于您的r)是当前计数,total是代表最终计数的变量。我们将与count统一在我们完成计数时:在流的末尾。

在发布的原始程序中,有许多Singleton变量(变量永远不会与任何内容统一,例如w)。这通常表示错误,并会引起警告。还记得Prolog是一种逻辑语言,退后一步并认为“我实际上试图用这些变量来做些什么?”。它还可以帮助将问题分解为较小的块,而不是试图编写一个可以完成所有操作的谓词。

Here's my attempt (ISO predicates):

% open Src, count vowels, close stream, print to console
count_vowels_in(Src) :-
    open(Src, read, Stream),
    count(Stream, Total),
    close(Stream),
    % cutting here because our Stream is now closed, any backtracking will break things that rely on it
    % you could also put this after at_end_of_stream/1 in count_/3
    % not sure what best practices are here
    !,
    write(Total).

% just a nice wrapper to get started counting with the initial count set to 0
count(Stream, Total) :-
    count_(Stream, 0, Total).

% at end of stream, Count = Total and we're done
count_(Stream, Count, Count) :-
    at_end_of_stream(Stream).

% read from stream recursively, incrementing Count as needed
count_(Stream, Count0, Total) :-
    \+at_end_of_stream(Stream),
    get_char(Stream, Char),
    char_value(Char, Value),
    Count1 is Count0 + Value,
    % recursively call count_, but now with our new Count1 value instead, carrying forward the results
    count_(Stream, Count1, Total).

char_value(Char, 1) :-
    vowel(Char).
char_value(Char, 0) :-
    \+vowel(Char).

vowel(a).
vowel(e).
vowel(i).
vowel(o).
vowel(u).

The biggest difference is that I use two variables for keeping track of the count. Count (equivalent to your R) is the current count, and Total is a variable representing the final count. We unify Total with Count when we are finished counting: at the end of the stream.

In the original program posted, there were many singleton variables (variables that are never unified with anything, for example W). This is usually indicative of a bug and will generate warnings. Remember that Prolog is a logical language, it can be good to take a step back and think "what am I actually trying to do with these variables?". It can also help to break the problem down into smaller chunks instead of trying to write one predicate that does everything.

原来分手还会想你 2025-02-02 06:16:23

我可能会这样处理:

  • 整个文件中的slurp作为字符列表。
  • 遍历该列表,并将其包含的元音计数。
  • 写塔利。

类似的东西

findall(C, ( get0(V) , V \= -1 , char_code(C,V) ), Cs).

应该足以使文字含糊。

然后,沿着这些界线:

count_vowels :-
    findall(C, ( get0(V) , V \= -1 , char_code(C,V) ), Cs),
    count_vowels(Cs,N),
    writeln( total_vowels : N )
    .

count_vowels( S  , N ) :- string(S), !, string_chars(S,Cs), count_vowels(Cs,N) .
count_vowels( Cs , N ) :- count_vowels(Cs,0,N) .

count_vowels( []     , N , N ) .
count_vowels( [C|Cs] , T , N ) :- tally(C,T,T1), count_vowels(Cs,T1,N).

tally( C , M , N ) :- vowel(C), !, N is M+1 .
tally( _ , N , N ) .

vowel( a ).
vowel( e ).
vowel( i ).
vowel( o ).
vowel( u ).

I might approach it like this:

  • Slurp in the entire file as a list of characters.
  • Traverse that list and tally the vowels it contains.
  • Write the tally.

Something like

findall(C, ( get0(V) , V \= -1 , char_code(C,V) ), Cs).

should suffice for slurping the text.

And then, something along these lines:

count_vowels :-
    findall(C, ( get0(V) , V \= -1 , char_code(C,V) ), Cs),
    count_vowels(Cs,N),
    writeln( total_vowels : N )
    .

count_vowels( S  , N ) :- string(S), !, string_chars(S,Cs), count_vowels(Cs,N) .
count_vowels( Cs , N ) :- count_vowels(Cs,0,N) .

count_vowels( []     , N , N ) .
count_vowels( [C|Cs] , T , N ) :- tally(C,T,T1), count_vowels(Cs,T1,N).

tally( C , M , N ) :- vowel(C), !, N is M+1 .
tally( _ , N , N ) .

vowel( a ).
vowel( e ).
vowel( i ).
vowel( o ).
vowel( u ).
~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文