Skip to content

Instantly share code, notes, and snippets.

@yuri-potatoq
Last active March 24, 2026 14:17
Show Gist options
  • Select an option

  • Save yuri-potatoq/250ef624ca810a776328d1068c81b967 to your computer and use it in GitHub Desktop.

Select an option

Save yuri-potatoq/250ef624ca810a776328d1068c81b967 to your computer and use it in GitHub Desktop.

Revisions

  1. yuri-potatoq revised this gist Mar 24, 2026. 1 changed file with 141 additions and 60 deletions.
    201 changes: 141 additions & 60 deletions main.py
    Original file line number Diff line number Diff line change
    @@ -1,6 +1,19 @@


    class Clipboard:
    ALLOWED_COMMANDS = [
    # delete/pop the last inserted content
    'd',
    # copy/push an content to clipboard
    'c',
    # paste/pop the last inserted content
    'p',
    # finish the repl
    'q',
    # show/print the stack representation
    's',
    ]

    def __init__(self, stack: Stack):
    self.stack = stack

    @@ -13,6 +26,121 @@ def paste_and_consume(self) -> str | None:
    def paste_text(self) -> str | None:
    return self.stack.get()

    def parse_line(self, line: str) -> tuple[str, str | None] | ValueError:
    command, content = "", None

    for idx, lt in enumerate(line):
    if idx == 0:
    if not lt in self.ALLOWED_COMMANDS:
    return ValueError(f"Commando [{lt}] não implementado: [{self.ALLOWED_COMMANDS}].")

    command = lt
    continue
    else:
    if lt == " ":
    continue
    else:
    content = line[idx:]
    break

    return (command, content)

    def run(self):
    while True:
    match self.parse_line(input("> ")):
    case ('c', content):
    if not content:
    print("comando de [copy] precisa de conteúdo para ser copiado.")
    continue
    self.copy_text(content)
    case ('d', None):
    if not self.paste_and_consume():
    print("Clipboard já está vazio.")
    case ('p', None):
    text = self.paste_text()
    if not text:
    print("Sem items no clipboard")
    else:
    print(text)
    case ('q', None):
    print("")
    return
    case ('s', None):
    print(f"Stack:\n{self.stack}")
    case ValueError() as err:
    print(err)


    from dataclasses import dataclass
    from enum import Enum

    class TokenKind(Enum):
    WORD = 1
    SPACE = 2

    @dataclass
    class TextEditorToken:
    content: str
    kind: TokenKind

    class TextEditor:
    def __init__(self, stack: Stack):
    self.stack = stack

    def write(self, line):
    for it in self.parse_line(line):
    self.stack.push(it)

    def undo(self):
    self.stack.pop()

    def parse_line(self, line) -> list[TextEditorToken]:
    items = []
    cursor = 0
    line_sz = len(line)

    def peek_next() -> str | None:
    if cursor+1 > line_sz-1:
    return None

    return line[cursor+1]

    def collect_word(is_space: bool) -> str:
    nonlocal cursor
    word = ""
    while True:
    tk = peek_next()
    if not tk:
    return word

    if is_space:
    if tk == " ":
    word += tk
    cursor += 1
    else:
    return word
    else:
    if tk != " ":
    word += tk
    cursor += 1
    else:
    return word


    while cursor < line_sz:
    char = line[cursor]
    print(f"char [{char}]")
    print(f"cursor [{cursor}]")
    if char == " ":
    space = char + collect_word(True)
    items.append(TextEditorToken(space, TokenKind.SPACE))
    else:
    word = char + collect_word(False)
    items.append(TextEditorToken(word, TokenKind.WORD))

    cursor += 1
    return items


    # TODO: make it generic over type T
    class Stack:
    @@ -52,75 +180,28 @@ def __str__(self) -> str:
    counter -= 1
    return stack_str


    ALLOWED_COMMANDS = [
    # delete/pop the last inserted content
    'd',
    # copy/push an content to clipboard
    'c',
    # paste/pop the last inserted content
    'p',
    # finish the repl
    'q',
    # show/print the stack representation
    's',
    ]


    def run_clipboard():
    clipboard = Clipboard(Stack())

    while True:
    match parse_line(input("> ")):
    case ('c', content):
    if not content:
    print("comando de [copy] precisa de conteúdo para ser copiado.")
    clipboard.copy_text(content)
    case ('d', None):
    if not clipboard.paste_and_consume():
    print("Clipboard já está vazio.")
    case ('p', None):
    text = clipboard.paste_text()
    if not text:
    print("Sem items no clipboard")
    else:
    print(text)
    case ('q', None):
    print("")
    return
    case ('s', None):
    print(f"Stack:\n{clipboard.stack}")
    case ValueError() as err:
    print(err)

    def main():
    try:
    run_clipboard()
    te = TextEditor(Stack())
    te.write("Olá mundo eu gosto de você")
    te.undo()
    te.undo()
    te.undo()
    te.undo()
    te.undo()
    te.undo()
    te.undo()
    te.write("isso é um test")


    except KeyboardInterrupt:
    print("")
    except Exception as err:
    print(f"Erro desconhecido: {err.args}")

    def parse_line(line: str) -> tuple[str, str | None] | ValueError:
    command, content = "", None

    for idx, lt in enumerate(line):
    if idx == 0:
    if not lt in ALLOWED_COMMANDS:
    return ValueError(f"Commando [{lt}] não implementado: [{ALLOWED_COMMANDS}].")

    command = lt
    continue
    else:
    if lt == " ":
    continue
    else:
    content = line[idx:]
    break

    return (command, content)


    # entrypoint guard
    if __name__ == '__main__':
    main()
    main()cat: s: No such file or directory
  2. yuri-potatoq created this gist Mar 21, 2026.
    126 changes: 126 additions & 0 deletions main.py
    Original file line number Diff line number Diff line change
    @@ -0,0 +1,126 @@


    class Clipboard:
    def __init__(self, stack: Stack):
    self.stack = stack

    def copy_text(self, text):
    self.stack.push(text)

    def paste_and_consume(self) -> str | None:
    return self.stack.pop()

    def paste_text(self) -> str | None:
    return self.stack.get()


    # TODO: make it generic over type T
    class Stack:
    def __init__(self):
    self.items = list()
    self.size = 0

    def push(self, item):
    # ok, you can use append, but only this one '-'
    self.items.append(item)
    self.size += 1

    def pop(self):
    if self.size < 1:
    return None

    # don't use .pop(), use your brain instead!
    it = self.items[self.size-1]
    self.items = self.items[:self.size-1]
    self.size -= 1
    return it

    def get(self):
    if self.size < 1:
    return None

    # don't use get(-1) or arr[-1], use your brain instead
    return self.items[self.size-1]

    def __str__(self) -> str:
    stack_str = ""

    # don't use reverse, use your brain instead!
    counter = len(self.items)-1
    while counter >= 0:
    stack_str += f"{self.items[counter]} -> [{counter}]\n"
    counter -= 1
    return stack_str


    ALLOWED_COMMANDS = [
    # delete/pop the last inserted content
    'd',
    # copy/push an content to clipboard
    'c',
    # paste/pop the last inserted content
    'p',
    # finish the repl
    'q',
    # show/print the stack representation
    's',
    ]


    def run_clipboard():
    clipboard = Clipboard(Stack())

    while True:
    match parse_line(input("> ")):
    case ('c', content):
    if not content:
    print("comando de [copy] precisa de conteúdo para ser copiado.")
    clipboard.copy_text(content)
    case ('d', None):
    if not clipboard.paste_and_consume():
    print("Clipboard já está vazio.")
    case ('p', None):
    text = clipboard.paste_text()
    if not text:
    print("Sem items no clipboard")
    else:
    print(text)
    case ('q', None):
    print("")
    return
    case ('s', None):
    print(f"Stack:\n{clipboard.stack}")
    case ValueError() as err:
    print(err)

    def main():
    try:
    run_clipboard()
    except KeyboardInterrupt:
    print("")
    except Exception as err:
    print(f"Erro desconhecido: {err.args}")

    def parse_line(line: str) -> tuple[str, str | None] | ValueError:
    command, content = "", None

    for idx, lt in enumerate(line):
    if idx == 0:
    if not lt in ALLOWED_COMMANDS:
    return ValueError(f"Commando [{lt}] não implementado: [{ALLOWED_COMMANDS}].")

    command = lt
    continue
    else:
    if lt == " ":
    continue
    else:
    content = line[idx:]
    break

    return (command, content)


    # entrypoint guard
    if __name__ == '__main__':
    main()