#esoteric-python

1 messages · Page 31 of 1

fleet bridge
#

Use .__iadd__() 🤯

#

I heard that it is faster because it copies less

mortal grotto
#

This is actually pretty new, was working fine in 3.9 as far as I recall correctly

distant salmon
#

Python really wants to keep track of which variables are local or not

#

Ye I just checked, it is an error even as far back as Python 2.7.18 (and probably much further back than that)

mortal grotto
#

Then I messed something up

burnt pasture
#

this is trying to update a global in a function. you should avoid that in any case.

burnt pasture
distant salmon
burnt pasture
distant salmon
#

I'm talking about Python implementations of algorithms and data structures. I would say it is a relatively common to see people do .append to non-local lists there.

#

A basic example would be building graphs

#

For example this is a natural way to build directed graphs with capacities (used for max-flow)

V = []
C = []
F = []
def add_edge(u, v, cap, rcap = 0):
    V.append(v)
    V.append(u)
    C.append(cap)
    C.append(rcap)
burnt pasture
distant salmon
#

I'm definitely the small self-contained examples kind of guy

burnt pasture
#

ok, that explains it.

earnest wing
#

my production code is exclusively global variables using interior mutability, also dunders

quartz wave
#

well there's a reason
global A
exists

burnt pasture
quartz wave
vast wave
#

shit like this is why i don't enjoy python as much as other languages

#

the scope definition of certain things is wonky at best

mortal grotto
#

python often tries to implement some things, which prohibit unwished behaviour. Same as sum(Iterable[str], begin="")

#

So it would work, but is a bad practice and so python says nuh uh

restive void
night quarryBOT
#

@restive void :white_check_mark: Your 3.11 eval job has completed with return code 0.

foobarbat
true basalt
#

!e this is what I call the f'in hell

import time
_f = time.sleep
_f_ = int
f = _f_(f"5")
_f(_f_(_f_(_f_(f"{f'{_f_(f)}'}"))))
night quarryBOT
#

@true basalt :warning: Your 3.11 eval job has completed with return code 0.

[No output]
mint rain
#

!e

A = [0,0,0,0]
x = A[x] = 3
print(A)```
night quarryBOT
#

@mint rain :white_check_mark: Your 3.11 eval job has completed with return code 0.

[0, 0, 0, 3]
sonic birch
mint rain
#

this is why i love python

#

only learned this trick bc i saw it somewhere up in this channel

#

x[i] = i idk when ill use it tho

sonic birch
#

Even chatgpt is confused) Looks like Mandela effect to me

#

Oh, I wouldn't be so sure:)

turbid dragon
#

!e

A = [0,0,0,0,0,0,0,0]
x = A[x] = 3
print(A)```
night quarryBOT
#

@turbid dragon :white_check_mark: Your 3.11 eval job has completed with return code 0.

[0, 0, 0, 3, 0, 0, 0, 0]
turbid dragon
#

ahhh

sonic birch
#

Guys, does anybody know a way how to override getting attribute in super class (when calling super().attribute?
I tried

class Meta(type):

  def __getattr__(cls, key):
    print('meta getattribute', key)

    return None


class Parent(metaclass=Meta):
  def __getattr__(cls, key):    
    print('parent getattribute', key)

    return None

class Child(Parent):
  def foo(self):
    super().foo()

child = Child()

child.foo()

But I get AttributeError: 'super' object has no attribute 'foo'

burnt pasture
sonic birch
burnt pasture
#

hmm, i'm not sure how to do that.

lime wave
#

how can I space words in python

import re

text = "hellobrotherhowareyou"

# Split the string into words based on camelCase or PascalCase conventions
split_text = re.findall(r'[A-Za-z][a-z]*', text)

# Join the words with a space between them
spaced_text = " ".join(split_text)

print(spaced_text)
``` I asked an ai but it  just printed "hellobrotherhowareyou"
burnt pasture
burnt pasture
karmic pumice
#

!e

(hgjntyr5bu6f56htgr79b8nyfj65htg79bn8jryf:=lambda:(u7oiyghtvbu89hybg7ijo:={},bhjnm_kg:=3,EeeeeeeeeEeeeeeeeeeEeeeeeeeeeeEeeeeeeeeeeeeeeeEeeeeeeeeeeeEeeeeeeeeeEeeeeeeeeEeeeeeeeee:=5,Htgjryu5f6i:="fizz",V5c67bgFsuxizjtd3475Vvc:="buzz",u7oiyghtvbu89hybg7ijo.__setitem__(bhjnm_kg, Htgjryu5f6i),u7oiyghtvbu89hybg7ijo.__setitem__(EeeeeeeeeEeeeeeeeeeEeeeeeeeeeeEeeeeeeeeeeeeeeeEeeeeeeeeeeeEeeeeeeeeeEeeeeeeeeEeeeeeeeee, V5c67bgFsuxizjtd3475Vvc),func_func_func_for_func_funcfuncfunc_vbcgdfxhe4:=lambda S7c4ALBz8WjVBNse5raIrfKzyrGwiDXAWjUmuwsG: ''.join([u7oiyghtvbu89hybg7ijo[DdzlL7BsfRlW0TqER0HV5JDd3j7uu750AefzOB2k] for DdzlL7BsfRlW0TqER0HV5JDd3j7uu750AefzOB2k in u7oiyghtvbu89hybg7ijo if not(S7c4ALBz8WjVBNse5raIrfKzyrGwiDXAWjUmuwsG%DdzlL7BsfRlW0TqER0HV5JDd3j7uu750AefzOB2k)]) or str(S7c4ALBz8WjVBNse5raIrfKzyrGwiDXAWjUmuwsG),list(map(print, map(func_func_func_for_func_funcfuncfunc_vbcgdfxhe4, range(1, 101)))),None)[-1])()
night quarryBOT
#

@karmic pumice :white_check_mark: Your 3.11 eval job has completed with return code 0.

001 | 1
002 | 2
003 | fizz
004 | 4
005 | buzz
006 | fizz
007 | 7
008 | 8
009 | fizz
010 | buzz
011 | 11
... (truncated - too many lines)

Full output: https://paste.pythondiscord.com/F5OP6MVIZRMK5CC2RG4WRCO3QU

vast wave
#

so HelloBrotherHowAreYou would be processed correctly

#

splitting a string just based on words is hard if not impossible to do without ai

#

we as humans have previous experience with words and, more importantly, misspelling of words, which is why you can read hellobroterhowru

#

how do you tell a computer to read that

#

just taking a wordlist and using that to split the string also wouldnt work properly, since certain words in that wordlist may appear in the string you want to split, where it contextually wouldnt make sense

#

eg hireggie might be recognized as "hire ggie"

#

that's the entire point of even using ai, letting the computer figure out how to do it for us

#

so ai might be your best bet here, but it'd still be hard to train and use a neural net in the first place

restive void
#

The task is also fundamentally impossible to do unambiguously, AI or not. There are many strings that can be split in several legitimate word lists.
E.g. "nappythonghost" could be nap-python-ghost or nappy-thong-host.

odd moat
#

also the regex from the ai's answer would not do that, the corect one would be: '[A-Z][a-z]*' (i think)

restive void
odd moat
#

o really? man regex is confusing

restive void
#

It's because * is greedy by default. If it was *? you'd be right

#

(but then it wouldn't correctly get the words)

sonic birch
# sonic birch Guys, does anybody know a way how to override getting attribute in super class (...

!e

def wrapper(*args, **kwargs):
    return None

def root():
    class MetaRoot(type):
        def new(cls, *args, **kwargs):
            if args:
                for c in args[1][:-1]:
                    methods = [m for m in c.dict if not m.startswith('')]
                    for m in methods:
                        setattr(args[1][-1], m, wrapper)
            return super().__new(cls, *args, **kwargs)
    return MetaRoot('Root', (), {})

class Parent:
    pass
class Child:
    def foo(self):
        return super().foo()
class Mixed(Child, Parent, root()):
    pass
m = Mixed()
print(m.foo())

The only way I have found till now is this

UDP: strange, in works in python 3.10 on my local

night quarryBOT
#

@sonic birch :x: Your 3.11 eval job has completed with return code 1.

001 | Traceback (most recent call last):
002 |   File "/home/main.py", line 23, in <module>
003 |     print(m.foo())
004 |           ^^^^^^^
005 |   File "/home/main.py", line 19, in foo
006 |     return super().foo()
007 |            ^^^^^^^^^^^
008 | AttributeError: 'super' object has no attribute 'foo'
brazen geyser
#

something like this to start off with

#

!e

import builtins
import sys

def patched_super():
  caller_locals = sys._getframe().f_back.f_locals
  self = caller_locals['self']
  cls: typing.Type = caller_locals['__class__']
  parent = cls.mro()[1]
  parent_getattr = parent.__getattr__

  class Proxy:
    def __getattribute__(proxu_self, item):
      return parent_getattr(self, item)

  return Proxy()

builtins.super = patched_super

class Parent:
  def __getattr__(self, item):
    print('parent getattr', item)
    return None

class Child(Parent):
  def foo(self):
    super().foo()

child = Child()

child.foo()
night quarryBOT
#

@brazen geyser :x: Your 3.11 eval job has completed with return code 1.

001 | parent getattr foo
002 | Traceback (most recent call last):
003 |   File "/home/main.py", line 30, in <module>
004 |     child.foo()
005 |   File "/home/main.py", line 26, in foo
006 |     super().foo()
007 | TypeError: 'NoneType' object is not callable
restive void
#

Make sure to really call the patched super super though or it will not work ;)

sonic birch
sonic birch
# sonic birch !e ```py def wrapper(*args, **kwargs): return None def root(): class Me...

!e

def wrapper(*args, **kwargs):
    return None

def root():
    class MetaRoot(type):
        def __new__(cls, *args, **kwargs):
            print(args)
            if args:
                for c in args[1][:-1]:
                    methods = [m for m in c.__dict__ if not m.startswith('_')]
                    for m in methods:
                        setattr(args[1][-1], m, wrapper)
            return super().__new__(cls, *args, **kwargs)
    return MetaRoot('Root', (), {})

class Parent:
    pass
class Child:
    def foo(self):
        return super().foo()
class Mixed(Child, Parent, root()):
    pass
m = Mixed()
print(m.foo())

Fixed!

night quarryBOT
#

@sonic birch :white_check_mark: Your 3.11 eval job has completed with return code 0.

001 | ('Root', (), {})
002 | ('Mixed', (<class '__main__.Child'>, <class '__main__.Parent'>, <class '__main__.Root'>), {'__module__': '__main__', '__qualname__': 'Mixed'})
003 | None
versed eagle
#

!e

from ctypes import (
    py_object as PyObject_p,
    c_int as int32_t,
    c_ssize_t as Py_ssize_t,
    sizeof as sizeof,
)

true = True
false = False

true_v = int32_t.from_address(
    id(true) + sizeof(Py_ssize_t * 2) + sizeof(PyObject_p)
)
false_v = int32_t.from_address(
    id(false) + sizeof(Py_ssize_t * 2) + sizeof(PyObject_p)
)

print(f"""\
before change:
    {true_v = }
    {false_v = }
""")

true_v.value = 0
false_v.value = 1

print(f"""\
after change:
    {true_v = }
    {false_v = }
""")

print(f"""\
True: {+true}
False: {+false}
""")
night quarryBOT
#

@versed eagle :white_check_mark: Your 3.11 eval job has completed with return code 0.

001 | before change:
002 |     true_v = c_int(1)
003 |     false_v = c_int(0)
004 | 
005 | after change:
006 |     true_v = c_int(0)
007 |     false_v = c_int(1)
008 | 
009 | True: 0
010 | False: 0
versed eagle
#

why doesnt the value of false change also?

rugged sparrow
#

!e booleans are a subclass of int, so they have a ob_size field as well. You would need to change that (ignoring the fact that internally python checks bools by identity and not value)

from ctypes import *
class Boolean(Structure):
    _fields_ = [
            ('ob_refcnt', c_ssize_t),
            ('ob_type', py_object),
            ('ob_size', c_ssize_t),
            ('bool_val', c_int)
    ]
    def __repr__(self):
      ob_refcnt = self.ob_refcnt
      ob_type = self.ob_type
      ob_size = self.ob_size
      bool_val = self.bool_val
      return f'Boolean({ob_refcnt=}, {ob_type=}, {ob_size=}, {bool_val=})'

T_struct = Boolean.from_address(id(True))
F_struct = Boolean.from_address(id(False))
print(f'{T_struct = }')
print(f'{F_struct = }')

T_struct.bool_val = 0
F_struct.ob_size = 1
F_struct.bool_val = 1

true, false = True, False

print(f"""\
True: {+true}
False: {+false}
""")
night quarryBOT
#

@rugged sparrow :white_check_mark: Your 3.11 eval job has completed with return code 0.

001 | T_struct = Boolean(ob_refcnt=56, ob_type=<class 'bool'>, ob_size=1, bool_val=1)
002 | F_struct = Boolean(ob_refcnt=79, ob_type=<class 'bool'>, ob_size=0, bool_val=0)
003 | True: 0
004 | False: 1
versed eagle
#

why does the size need to be changed though

#

im not increasing it past 2**32 -1

rugged sparrow
#

if ob_size is zero, there is assumed to be no numerical data to calculate the value.

versed eagle
#

why would the size be zero though

#

oh

#

nvm

rugged sparrow
#

there are several shortcuts for zero (and False) that use ob_size being zero as a flag

sage viper
#

For a parameter with a default value, the corresponding argument may be omitted from a call, in which case the parameter’s default value is substituted.

A parameter is a variable in a function definition. It is a placeholder and hence does not have a concrete value. An argument is a value passed during function invocation.

rubberduck answered my own question

rugged sparrow
#

@dry mirage have you had any issues updating einspect's hooking capability to 3.12+?

#

i think my setattr trick is broken

quartz wave
#

i think all of my C extensions are gonna break in 3.12

#

that's not good

#

should've listened to godlygeek

rugged sparrow
#

i figured it out, setattr expects normal dict locations and now the internal types have their dicts stored in a different location

quartz wave
rugged sparrow
#

oh yea those are gonna break hard

dry mirage
#

thought that still worked last I tried firT

rugged sparrow
#

there is some funky stuff involving type dicts now

dry mirage
#

the managed instance dictionary?

rugged sparrow
#

yea

#

i think?

#

in my testing at one point it manifested a second instance dict for int

#

one that had my hooks and one that it had before hand

#

setattr when tp_dict is null seems to manifest a dict, even if the type has a managed dict stored in the interpreter state

dry mirage
night quarryBOT
#

src/einspect/structs/py_object.py line 248

def instance_dict(self) -> ptr[PyObject[dict, Any, Any]] | None:```
rugged sparrow
#

i just fixed mine to clear out the manifested dict so that the class state remained consistent

#

probably not the best solve but itll work

dry mirage
#

wonder if it affects c extension types as well, might be an upstream bug in setattr

rugged sparrow
#

it shouldn't since the only reason these types were broken is because they have cached dicts that are shared across interpreters

brazen geyser
night quarryBOT
#

Objects/typeobject.c lines 224 to 229

if (self->tp_flags & _Py_TPFLAGS_STATIC_BUILTIN) {
    PyInterpreterState *interp = _PyInterpreterState_GET();
    static_builtin_state *state = _PyStaticType_GetState(interp, self);
    assert(state != NULL);
    return state->tp_dict;
}```
rugged sparrow
#

since its an internal type flag _Py_TPFLAGS_STATIC_BUILTIN i don't think its a bug in setattr

stark granite
#

i dont understand lol

>>> (lambda:(lambda t:t(None,f).run())(t:=__import__("threading").Thread),t(None,f).run())()
<stdin>:1: SyntaxWarning: 'tuple' object is not callable; perhaps you missed a comma?
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
NameError: name 't' is not defined
>>> 
#

in what place is it not defined

#

wait

#

i think i realised what was wrong

#

, has higher priority

#

so you need to put () around lambda's code

pastel stump
#

I'm trying to implement __setattr__ for a class that also uses getters and setters using the property class with the following implementation:

def __setattr__(self, name: str, value):
  if isinstance(value, property) or callable(value):
    super().__setattr__(name, value)
  else:
    getattr(self, "__dynamic_set_"+name)(self, self, value)

The __dynamic_set_ function is a predefined setter function that is used in conjunction with the property() class. The issue is that when i set the variable with setattr and i print said variable, the output will always be <property object at 0x*********>.

The getattr portion works perfectly fine in another portion of the script. What on earth am I doing wrong here?

versed eagle
#

a little bit unrelated but why do you pass self twice into the dynamic set?

versed eagle
#

like, an example usecase

#

and what you want it to do vs. what it does

pastel stump
#

I'm trying to implement a class that will keep track of certain modified variables. Basically: You add a property using the following function def __add_tracked_property(self, property_type, property_name, property_value=None), and it automagically creates the variable, including the property() statement in order to add a setter that will keep track of modified variables.

The specific usecase is a generic API client that will self-populate it's variables. In order to save on bandwidth/database usage, I only want to send variables that have been modified without bothering the end-user/programmer with keeping track of everything

#

Because of the dynamic nature of it all, I still need access to setattr without overriding the property() instance.

versed eagle
#

call .__set__ on the property instance

#

directly

#

at least, thats what it sounds like you want

pastel stump
#

So basically replace the getattr line with getattr(self, name).__set__(self, value)?

versed eagle
#

if its a property

#

yeah

#

property objects have __set__ and __get__ for managing themselves

pastel stump
#
def __setattr__(self, name: str, value):
  if hasattr(self, name) and isinstance(getattr(self, name), property):
    getattr(self, name).__set__(self, value)
  else:
    super().__setattr__(name, value)

More like this then?

#

Because that does not work either, and i still get just the <property object at 0x****> when i print

versed eagle
#

you still havent explained to me what you actually want to do

versed eagle
pastel stump
#

As stated before, i want to be able to use the property class in conjunction with setattr.

If I assign a setter for a certain variable, and use setattr(obj, thatcertainvariable, somevalue), it will override the property that was just assigned, and replace it with the actual value

#

I want to be able to use setattr on all variables, property or normal variable

versed eagle
#

the idea behind the class isn't the most relevant; what i need to know is

  • what the intended behaviour of your function is
  • what it actually does
  • an example usecase of this, so i can see how the function is being invoked
pastel stump
#

Hang on, debugging atm. Something is not quite right

fleet bridge
versed eagle
#

could be a static or class method ;)

pastel stump
fleet bridge
#

Probably you have mangling issues

#

Dont use __names if not necessary

pastel stump
#

Somehow in a refactor, it broke. Not sure why -_-

#

So the setter was never called. I'll post a full code example in a minute, with the reasoning behind it 😛

#

Riiiight..... I'm just kinda running in circles 😛

class DynamicVariableMixin():
    '''
    Used to be able to store and keep track of dynamic variables
    '''
    _updated_vars=None
    _dynamic_variables = {}

    def __add_method__(self, property_type, property_name):
        def set_attribute(self, obj, property_value, **kwargs):
            print("Setting")
            try:
                if property_type == type(property_value):
                    self._dynamic_variables[property_name] = property_value
                else:
                    raise TypeError
            finally:
                pass
        def get_attribute(self, *args, **kwargs):
            
            return self._dynamic_variables[property_name]
        setattr(self.__class__, '__dynamic_set_'+ property_name, set_attribute)
        setattr(self.__class__, '__dynamic_get_'+ property_name, get_attribute)
        setattr(self.__class__, property_name, 
            property(
                getattr(self, '__dynamic_get_'+ property_name), 
                getattr(self, '__dynamic_set_'+ property_name)
            )
        )

    def __add_tracked_property__(self, property_type, property_name):
        self.__add_method__(property_type, property_name)

This works, only on a class level (which i dont want because of obvious reasons). When i remove the .__class__ from setattr in order to set the getter/setter, it completely breaks and no longer uses the getter/setter

Implementation example:

class Test(DynamicVariableMixin):
    a = "Hello"

t1 = Test()
t2 = Test()

t1.__add_tracked_property__(str, "myvariable")
t1.myvariable = "Hello!"
print(t2.myvariable)

t2.myvariable currently resolves without any issue to "Hello!", which shouldn't happen.

#

Why the convoluted mess? I'm declaring some classes dynamically using input from an API. Object properties are set dynamically using the API response, and kept track of using the class above (WIP of course).

This is so the end-user/programmer does not have to fiddle with keeping track of modified properties of said object/instance when saving (patching) back to the API

fleet bridge
#

Why are you even setring __dynamic_set/get attributes? You are not using them

#

!e ```py
n = 15

s = f'<{n}>'
while True:
# print(f'{s} [{len(s)}]')
if '|0' in s:
s = s.replace('|0', '0||||||||||', 1)
elif '.>' in s:
s = s.replace('.>', '>', 1)
elif '.|' in s:
s = s.replace('.|', '-.', 1)
elif '0-' in s:
s = s.replace('0-', '1', 1)
elif '1-' in s:
s = s.replace('1-', '2', 1)
elif '2-' in s:
s = s.replace('2-', '3', 1)
elif '3-' in s:
s = s.replace('3-', '4', 1)
elif '4-' in s:
s = s.replace('4-', '5', 1)
elif '5-' in s:
s = s.replace('5-', '6', 1)
elif '6-' in s:
s = s.replace('6-', '7', 1)
elif '7-' in s:
s = s.replace('7-', '8', 1)
elif '8-' in s:
s = s.replace('8-', '9', 1)
elif '9-' in s:
s = s.replace('9-', '-0', 1)
elif '<-' in s:
s = s.replace('<-', '<1', 1)
if '-' not in s:
break
elif '9' in s:
s = s.replace('9', '8|', 1)
elif '8' in s:
s = s.replace('8', '7|', 1)
elif '7' in s:
s = s.replace('7', '6|', 1)
elif '6' in s:
s = s.replace('6', '5|', 1)
elif '5' in s:
s = s.replace('5', '4|', 1)
elif '4' in s:
s = s.replace('4', '3|', 1)
elif '3' in s:
s = s.replace('3', '2|', 1)
elif '2' in s:
s = s.replace('2', '1|', 1)
elif '1' in s:
s = s.replace('1', '0|', 1)
elif '00|' in s:
s = s.replace('00|', '0|', 1)
elif '0|' in s:
s = s.replace('0|', '0.||', 1)
else:
assert 0

n = int(s[1:-1])
print(n) # 16

night quarryBOT
#

@fleet bridge :white_check_mark: Your 3.11 eval job has completed with return code 0.

16
fleet bridge
#

Markov algo that does x+1

#

It isnot the best markov algo for this task, it can be a lot simpler (so it is kinda esoteric 😝)

#

(and it is bugged for some numbers)

#

(strictly speaking it is not a markov algo because of custom termination behaviour, but im too lazy to fix it)

pastel stump
fleet bridge
pastel stump
#

Right. Corrected that with

setattr(self.__class__, property_name, 
  property(
    get_attribute, 
    set_attribute
  )
)

Only issue now is that with the code above, object t2 still has the myvariable attribute due to the self.__class__ being used in setattr. If i remove the __class__, the property is somehow being overwritten when i assign a new value. The Setting in set_attribute never gets printed

rugged owl
fleet bridge
#

Exactly

tough willow
#

Why Not n += 1

fleet bridge
#

Because it is wrong channel for n+=1

tough willow
#

True

proper vault
#

!e ```py
def foo():
for a in [1,2,3]:
print(a)
for a in "abc":
print(a)
def trace(fr, ev, arg):
if fr.f_lineno == 3: fr.f_lineno = 5
return trace
import sys
sys.settrace(trace)

foo()

night quarryBOT
#

@proper vault :white_check_mark: Your 3.11 eval job has completed with return code 0.

001 | 1
002 | 2
003 | 3
restive void
#

Works in 3.9. Before it would complain about being unable to jump inside of a loop?

proper vault
#
    if fr.f_lineno == 3: fr.f_lineno = 5
ValueError: can't jump into the middle of a block
#

ye

restive void
#

Funnily it still does this sometimes

#

!e first a variant to show a bit more what's going on:

def foo():
    for a in [1,2,3]:
        print(a, "is a number")
    for a in None:
        print(a, "is a None?")

def trace(fr, ev, arg):
    if fr.f_lineno == 3:
        fr.f_lineno = 5
        fr.f_trace = None
    return trace

import sys
sys.settrace(trace)

foo()
night quarryBOT
#

@restive void :white_check_mark: Your 3.11 eval job has completed with return code 0.

001 | 1 is a None?
002 | 2 is a None?
003 | 3 is a None?
proper vault
#

yeah, the entire block stack must match to allow the jump, or you must be jumping out of a block

restive void
#

Block stack?

proper vault
#

block stack as in nested blocks, where a block is a for loop, with handler, etc

restive void
#

!e if the first loop has a break it seems to, well, break:

def foo():
    for a in [1,2,3]:
        print(a, "is a number")
        break
    for a in None:
        print(a, "is a None?")

def trace(fr, ev, arg):
    if fr.f_lineno == 3:
        fr.f_lineno = 6
        fr.f_trace = None
    return trace

import sys
sys.settrace(trace)

foo()
night quarryBOT
#

@restive void :white_check_mark: Your 3.11 eval job has completed with return code 0.

001 | 1 is a None?
002 | 2 is a None?
003 | 3 is a None?
restive void
#

huh. At least on 3.9 it does, whereas the previous code works

proper vault
#

IG no one really checks debugger jumps for backwards compat

#

or even debuggers in general tbh

restive void
#

There are tests

proper vault
#

ye, they get updated every version to match the behaviour of the new version

night quarryBOT
#

Objects/frameobject.c line 124

markblocks(PyCodeObject *code_obj, int len)```
proper vault
#

or well, the interesting part

restive void
#

(That reminds me, I should add a link to my talk on our internal company wiki now that the videos were released)

proper vault
#

you did a talk?

restive void
proper vault
#

noice

calm cove
#

!e

def weird(l):
    return max(list(filter(lambda x: x % 2 != 0, (sum(n) for n in zip(*l)))) or [0])


print(weird([[1, 2, 3], [7, 8, 9]]))
print(weird([[1, 2, 3], [4, 5, 6], [7, 8, 9]]))
print(weird([[1, 2, 3], [4, 5, 6], [7, 8, 9], [9, 10, 11]]))
night quarryBOT
#

@calm cove :white_check_mark: Your 3.11 eval job has completed with return code 0.

001 | 0
002 | 15
003 | 29
calm cove
#

This finds the largest odd sum of integer values of a column in a 2d list. The tricky part was figuring out how to do the check for the case of no uneven number and then use [0] instead. My initial approach of

intermediary = filter(lambda x: x % 2 != 0, (sum(n) for n in zip(*l)))
list(intermediary) if list(intermediary) != [] else [0]

or anything similar to that did not work as the call list() on the filter object, which is an iterator consumes it. And because you can't assign variables in a lambda function, I had to use

list(intermediary) or [0]

because bool(list(intermediary)) is False in the case that intermediary is empty. So then [0] is used

distant salmon
#

!e

def weird(A):
    return max((sum(col) for col in zip(*A) if sum(col) % 2), default = 0)

print(weird([[1, 2, 3], [7, 8, 9]]))
print(weird([[1, 2, 3], [4, 5, 6], [7, 8, 9]]))
print(weird([[1, 2, 3], [4, 5, 6], [7, 8, 9], [9, 10, 11]]))

I would have probably just done something like this ^.

night quarryBOT
#

@distant salmon :white_check_mark: Your 3.11 eval job has completed with return code 0.

001 | 0
002 | 15
003 | 29
icy cypress
#

is there a way to build this list using a list comprehension? maybe using the walrus operator?

new_lst = []
prev = 0
for i in lst:
    new_lst.append(i + prev)
    prev = i
    
>>> lst
[1, 1, 4, 1, 6, 1, 1, 3, 1, 3, 1, 4]
>>> new_lst
[1, 2, 5, 5, 7, 7, 2, 4, 4, 4, 4, 5]
fleet bridge
#

Bruh

#

!e ```py
l = [1,1,4,1,6,1,1,3,1,3,1,4]
l2 = [*map(int.add, l, l[1:]+[0])]
print(l2)

night quarryBOT
#

@fleet bridge :white_check_mark: Your 3.11 eval job has completed with return code 0.

[2, 5, 5, 7, 7, 2, 4, 4, 4, 4, 5, 4]
fleet bridge
#

Almost

icy cypress
#

map + int.add, thats beautiful

#

thanks

#

wait why is the last opposite

fleet bridge
#

!e ```py
l = [1,1,4,1,6,1,1,3,1,3,1,4]
l2 = [*map(int.add, l, [0]+l[:-1])]
print(l2)

night quarryBOT
#

@fleet bridge :white_check_mark: Your 3.11 eval job has completed with return code 0.

[1, 2, 5, 5, 7, 7, 2, 4, 4, 4, 4, 5]
fleet bridge
#

Fixed

icy cypress
#

wait maybe itertools has something

#

oh nice

#

do you think there is a more eficcient solution? that maybe avoids copying the list?

fleet bridge
#

Yeah, itertools.tee can dupe list iterator, then you can prepend 0 to one of them and iterate over using map

#

Idk how map behaves on inputs of unequal length

#

!d map

night quarryBOT
#
map

map(function, iterable, *iterables)```
Return an iterator that applies *function* to every item of *iterable*, yielding the results. If additional *iterables* arguments are passed, *function* must take that many arguments and is applied to the items from all iterables in parallel. With multiple iterables, the iterator stops when the shortest iterable is exhausted. For cases where the function inputs are already arranged into argument tuples, see [`itertools.starmap()`](https://docs.python.org/3/library/itertools.html#itertools.starmap).
restive void
#

Strange that it didn't also get a strict kwarg

icy cypress
#

there is itertools.pairwise but the default element for the first pair is the same element (and you cant override it apparently)

fleet bridge
#

!e ```py
import itertools as it
l = [1,1,4,1,6,1,1,3,1,3,1,4]
l2 = [*map(int.add, (i:=it.tee(l))[0], it.chain([0], i[1]))]
print(l2)

night quarryBOT
#

@fleet bridge :white_check_mark: Your 3.11 eval job has completed with return code 0.

[1, 2, 5, 5, 7, 7, 2, 4, 4, 4, 4, 5]
fleet bridge
#

Nice

restive void
#

!e

from itertools import*
l = [1,1,4,1,6,1,1,3,1,3,1,4]
l2 = [*map(sum, pairwise([0]+l))]
print(l2)
night quarryBOT
#

@restive void :white_check_mark: Your 3.11 eval job has completed with return code 0.

[1, 2, 5, 5, 7, 7, 2, 4, 4, 4, 4, 5]
#

@half escarp :white_check_mark: Your 3.11 eval job has completed with return code 0.

[2, 5, 5, 7, 7, 2, 4, 4, 4, 4, 5]
fleet bridge
icy cypress
#

Thanks all for the solutions

#

I will benchmark them and see whats faster

distant salmon
#

!e

l = [1,1,4,1,6,1,1,3,1,3,1,4]
l2 = l[:]
for i in range(1, len(l)):
  l2[i] += l[i - 1]
print(l2)
night quarryBOT
#

@distant salmon :white_check_mark: Your 3.11 eval job has completed with return code 0.

[1, 2, 5, 5, 7, 7, 2, 4, 4, 4, 4, 5]
versed eagle
#

then again, if we're micro-optimising, a generator or comprehension might be better than duplicating the list and then adding to it
ill go benchmark stuff once im on my computer

fleet bridge
versed eagle
#

lmao

#

if we're micro-optimising then we should use smaller variable names and less whitespace to minimise file-read and parsing times /j

fleet bridge
#

Just dont do anything and imagine correct result being printed

versed eagle
#

if we precalculate and preprint the result, then wait a really long time before benchmarking it, we can have a negative runtime (endtime will be before starttime so when calculating runtime endtime-starttime will be below 0)

versed eagle
distant salmon
#

Copying a list is one of those built in operations that runs blazingly fast

#

However, anything involving generators is Python code and will run rather slow

#

I've also never seen a performance gain from using tuples over lists. I would be really surprised if that could actually make it faster.

fleet bridge
#

I guess iterating over tuple can be a bit (tiny tiny bit) faster than iteration over list
Because tuple stores data in the object itself, but list allocates new memory and uses pointer to reach it
So less memory jumps => less time

fleet bridge
#

!e ```py
from dis import dis
dis('x in [1,2,3]')
dis('x in {1,2,3}')

#

Bot died?

languid hare
#

!e ```py
from dis import dis
dis('x in [1,2,3]')
dis('x in {1,2,3}')

night quarryBOT
#

@languid hare :white_check_mark: Your 3.11 eval job has completed with return code 0.

001 |   0           0 RESUME                   0
002 | 
003 |   1           2 LOAD_NAME                0 (x)
004 |               4 LOAD_CONST               0 ((1, 2, 3))
005 |               6 CONTAINS_OP              0
006 |               8 RETURN_VALUE
007 |   0           0 RESUME                   0
008 | 
009 |   1           2 LOAD_NAME                0 (x)
010 |               4 LOAD_CONST               0 (frozenset({1, 2, 3}))
011 |               6 CONTAINS_OP              0
... (truncated - too many lines)

Full output: https://paste.pythondiscord.com/7M4V7PH5M5NCV5TLYIN6MOTZK4

fleet bridge
#

Peepholes optimized these checks to not construct new list/set at runtime, so there is no difference in using literal tuples or literal lists

#

But in other cases if your list is known at compile time, you can use tuple instead

quartz wave
#

a list might actually iterate faster than a tuple and i still have no idea why

distant salmon
quartz wave
restive void
#

there's one less level of indirection

quartz wave
#

unless the pointer has to be loaded or something i think

restive void
distant salmon
#

Ah ok

simple moat
#
for i in input():d="cv"[i in"aeiouyAEIOUY"];print(end=(i,(d,d.upper())[i.isupper()])[i.isalpha()])
#

is it still possible to reduce length of this?

quartz wave
sick hound
fleet bridge
#

I think no

dense crypt
#

...this might be the wrong place to ask but this is Esoteric so here goes. I want to smash a portion of my animation and physics math AIO in a submodule named Colliction, the Color, Collision, and Projection Collection... is this too left brained?

#

basically it handles math functions between two tuples each less than length 4 with a factory approach

earnest wing
#

colliction is great, consider also adding another word into the mix

dense crypt
#

most of the words I would want to end in ion I would assume, but I definitwly havent actually thought of that, lol

#

I'm not an engineer, but I've been thinking about it for a while, and I think it could be a good educational and supplemental module

dense crypt
fleet bridge
#

Consider making all the words start with "col"

dense crypt
# fleet bridge Consider making all the words start with "col"

infeasible, this is essentially piece-meal math functions from core and core adjacent libraries, literally the biggest problem is naming things because like, half of it might be a vector and I have numpy so what if it just supports rich comparison?

#

why isnt it just a tuple?

dense crypt
#

@fleet bridge I'm trying to keep semi-natural names for things so that I can use Structural Pattern Matching to make it semi-lingual

dense forum
#

I prebake normals and my code instantly doubles in speed.

stark granite
#

my new milestone in oneliners!

(lambda data: (Path('analysis.txt').write_text('\n'.join(f"{char} {frequency:.3f}" for frequency, chars in sorted(((frequency, sorted(map(lambda char: char[0], filter(lambda info: info[1] == frequency, data.items())), key=ord)) for frequency in set(data.values())), key=lambda group: group[0], reverse=True) for char in chars))))((lambda total_length: {letter: occurrences / total_length for letter, occurrences in __import__('collections').Counter(s).items()})(len(s := ''.join(filter(lambda c: c in __import__('string').ascii_lowercase, map(str.lower, (Path := __import__('pathlib').Path)('text.txt').read_text()))))))
#

and without a single ; (or even :) hehe

#

prob there is a way to make that shorter (aside from shortening variable names obv and removing unnecessary spaces)

last locust
stark granite
#

:= dont count

#

and in strings too

#

ah wait

distant salmon
#

There are lambda: too

stark granite
#

lambdas'

last locust
#

lambda info: ...

stark granite
#

...

stark granite
#

i forgot about existence of those

#

lets just uhh....

#

ignore('lambda') :)

last locust
#

ignore('lambda.*:') :)

distant salmon
#

One small codegolf I can see is to change the sorted(..., reverse=True) to sorted(...)[::-1]

#

But that would add more :

stark granite
#

but like

#

the original code was separated into 3-4 function calls

#

(functions were oneliners)

#

so like

#

lets say i only did "thin" LTO

distant salmon
#

Here is one more codegolf

c in __import__('string').ascii_lowercase

can be changed to

'`'<c<'{'
#

It is also possible to do ```py
'a'<=c<='z'

versed eagle
#

i was joking

versed eagle
#

or, if its guaranteed that there's only one line in the file, *open('text.txt')

#

actually

#

why do you map str.lower

earnest wing
#

Big news! Development of hoopy is back!!!

versed eagle
#

oo you're doing codec stuff

#

#

you can put the bootstrap in a .pth file and then run python3 main_hoopy.py directly

versed eagle
# versed eagle why do you map str.lower
''.join(filter(lambda c: c in __import__('string').ascii_lowercase,map(str.lower, (Path := __import__('pathlib').Path)('text.txt').read_text())))

->

"".join(filter(lambda c:'`'<c<'{',open('text.txt').read().lower()))
# if the file only has 1 line,    str.lower(*open('text.txt')) is shorter
earnest wing
versed eagle
#

wdym by [cross incompatible]

earnest wing
#

there is no universal way to do it on install across platforms

versed eagle
#

ah

earnest wing
#

you can account for the most common use cases though

versed eagle
earnest wing
#

That's funny

#

sysconfig.get_path("platlib")

#

I guess the interpreter has to know about them

#

I'll probably make it an opt-in feature for the library then

stark granite
#

i actually kinda just wanted to make use of pathlib... for no reason really

stark granite
versed eagle
#

ah

humble blade
#

!e

from fishhook import hook

@hook(object)
def __matmul__(self, f):
  return f(self)

x = 2
sq = lambda x: x**2
x @= sq
print(x)
night quarryBOT
#

@humble blade :white_check_mark: Your 3.11 eval job has completed with return code 0.

4
humble blade
#

heh

fleet bridge
#

!e

from fishhook import hook
@hook(object)
def __matmul__(self, f):
  return f(self)

x = 2
x @= 3 .__rpow__
print(x) # 2**3 == 8
night quarryBOT
#

@fleet bridge :white_check_mark: Your 3.11 eval job has completed with return code 0.

8
fleet bridge
#

I like that

rugged sparrow
#

!e ```py
from fishhook import *
@hook(object)
def matmul(self, func):
return func(self)

print(123 @ str @ (lambda l:map(int, l)) @ list)
print(3456 @ str @ (lambda l:map(int, l)) @ list)```

night quarryBOT
#

@rugged sparrow :white_check_mark: Your 3.11 eval job has completed with return code 0.

001 | [1, 2, 3]
002 | [3, 4, 5, 6]
quartz wave
#

i just realized this is piping

languid hare
#

indeed it is

#

where's that one sebastiaan pycon talk

quartz wave
# languid hare where's that one sebastiaan pycon talk

Diving into the CPython source code can feel daunting. Whether you want to start contributing or just want to get a better understanding of Python by exploring its source code, it’s often difficult to know where to start or what you’re missing.

In my talk, I will show you around the CPython source code by implementing a new operator, a pipe ope...

▶ Play video
#

ok so for some reason i couldn't have tp_as_number populated in object

#

and it was supposed to originally be called a "decorator operator" but i just realized it's basically a pipe operator only now

#

nevertheless "decorator operator" sounds cooler and rhymes better

rugged sparrow
#

if so you hit the same bug that is the reason for fishhook's patch_object function

stark granite
quartz wave
#

so i couldn't even get python to run with it

rugged sparrow
#

most likely the same bug

#

python assumes a lot of things about object when calculating method resolution and slots inheritence, and if object has one of its tp_as_* structs populated it attempts to look at its base (which normally is NULL) which causes the crash

night quarryBOT
#

Objects/typeobject.c lines 6848 to 6851

if (type->tp_as_number != NULL && base->tp_as_number != NULL) {
    basebase = base->tp_base;
    if (basebase->tp_as_number == NULL)
        basebase = NULL;```
rugged sparrow
#

basebase is never checked against being NULL

quartz wave
#

simple fix then

#

yep

#

done

rugged sparrow
#

you also probably need to add the check to all of the tp_as_* sections

quartz wave
#

should it be PR'd to cpython or have you already done that?

rugged sparrow
#

it doesn't need to be fixed, its a correct assumption

quartz wave
#

ok then

rugged sparrow
#

it only breaks when you try and apply custom operations to object

rugged sparrow
# quartz wave simple fix then

yea its simple when you know where the issue is, when i was first adding support to fishhook for hooking the base object type i spent so many hours tracking down the root cause of the crash

#

and then more working out how to patch around the issue while maintaining stability

languid hare
#

entering real esoteric territory now

arctic skiff
restive void
arctic skiff
restive void
quartz wave
arctic skiff
#

well

quartz wave
#

they also did that with 3.11 beta and 3.12 dev

arctic skiff
#

didn't know about it

quartz wave
#

i could make it python 4.0.0 tbh

#

hold on

#

yay ```pycon

.\cpython-main\PCbuild\amd64\python.exe
Python 4.0.0 (main, Aug 15 2023, 14:40:15) [MSC v.1937 64 bit (AMD64)] on win32
Type "help", "copyright", "credits" or "license" for more information.

languid hare
stark granite
versed eagle
vapid magnet
#

Can anyone explain why it should work?

astral rover
#

that doesnt work does it?

vapid magnet
astral rover
#

til wtf

vapid magnet
#

First print is '3', second is '<class type>'

astral rover
#

second isnt hard to explain, its just returning the class type

vapid magnet
#

I tried to find more info about classes, but I dont find anything helpfull. Maybe I should try find more info about scopes

astral rover
#

i cant behave the firsts behaviour im really not sure why it loads a global there

#

i get where the naming is coming from though

distant salmon
night quarryBOT
#

@distant salmon :white_check_mark: Your 3.11 eval job has completed with return code 0.

001 | 3
002 | <class 'type'>
versed eagle
#

its because of name mangling

versed eagle
astral rover
#

i didnt realise it was as simple as a find and replace sorta thing for mangled names

vapid magnet
stark granite
fleet bridge
#

Good video about mangling tricks

quartz wave
#

!e ```py
@lambda x: globals().update(ᅠ=x)or x
class :
def init(_, x):
_.__x = x

print(ᅠ(...)._ᅠ____x)

night quarryBOT
#

@quartz wave :white_check_mark: Your 3.11 eval job has completed with return code 0.

Ellipsis
fleet bridge
#

Wut

#

!e ```py
@lambda x: print(ord(x.name[2]))
class :
...

night quarryBOT
#

@fleet bridge :white_check_mark: Your 3.11 eval job has completed with return code 0.

4448
fleet bridge
#

!charinfo 4448

night quarryBOT
fleet bridge
#

!charinfo ᅠ

night quarryBOT
quartz wave
#

0xffa0 is 65440

fleet bridge
#

Idk

vast wave
#

genuinely, how can you make something this convoluted

humble blade
#

this is more a name mangling thing than anything actually related to "core" OOP

quartz wave
#
>>> from dis import dis
>>> dis(r"""
... class __A__:
...     def __init__(_):
...             import __a.b
... """)

 ...

Disassembly of <code object __init__ at 0x0000016667C8F050, file "<dis>", line 3>:
  3           0 RESUME                   0

  4           2 LOAD_CONST               1 (0)
              4 LOAD_CONST               0 (None)
              6 IMPORT_NAME              0 (__a.b)
              8 STORE_FAST               1 (_A____a)

             10 RETURN_CONST             0 (None)
``` `__a.b` is imported in class `__A__` but the result gets stored into `_A____a`
#
  1. _A____a does not contain the class name (__A__)
  2. __a.b is left unmangled when importing, but it is stored into a mangled name (_A____a) anyway
lime wave
#

hello I have this anti bad word system something like this

badwords = ["badword", "bad"]
message = "bad"

if badwords in message.lower():
 print("true")

but people can bypass it by doing "badbad" how can I fix it

restive void
distant salmon
#

!e

badwords = ["badword", "bad"]
message = "bad"

if badwords in message.lower():
 print("true")
night quarryBOT
#

@distant salmon :x: Your 3.11 eval job has completed with return code 1.

001 | Traceback (most recent call last):
002 |   File "/home/main.py", line 4, in <module>
003 |     if badwords in message.lower():
004 |        ^^^^^^^^^^^^^^^^^^^^^^^^^^^
005 | TypeError: 'in <string>' requires string as left operand, not list
distant salmon
#

Ye it is. You should have

#

!e

badwords = ["badword", "bad"]
message = "bad"

if message.lower() in badwords:
 print("true")
night quarryBOT
#

@distant salmon :white_check_mark: Your 3.11 eval job has completed with return code 0.

true
fleet bridge
#

!e

badwords = ["badword", "bad"]
message = "bad".lower()

for bw in badwords:
 if bw in message:
  print("it is bad")
night quarryBOT
#

@fleet bridge :white_check_mark: Your 3.11 eval job has completed with return code 0.

it is bad
quartz wave
#

for anyone who missed ```pycon

.\cpython-main\PCbuild\amd64\python.exe
Python 4.0.0 (main, Aug 17 2023, 12:01:58) [MSC v.1937 64 bit (AMD64)] on win32
Type "help", "copyright", "credits" or "license" for more information.

5 |> 2 ** $
32
$
File "<stdin>", line 1
$
^
SyntaxError: template not in righthand side of pipe operation

#

piping and substitution

versed eagle
#

fun

fleet bridge
#

🤯

#

nice

hollow moth
#
def counter():
    x = 0
    def add():
        nonlocal x
        x += 1
        return x
    return add

add = counter()

print(add()) #  1
print(add()) #  2
languid hare
dusk breach
#
intron=''''''
exon='''
intron = input() or intron
print(f"{intron=:'^{len(intron)+6}}")
print(f"{exon=:'^{len(exon)+6}}")
print("exec(exon)")
'''
exec(exon)
stark granite
stark granite
#

prob due to last 6 letters

restive void
stark granite
#

wait

#

bruh

quartz wave
#

i just made it

lean lodge
#

Hello

quartz wave
#

hi

rugged owl
quartz wave
rugged owl
#

Pretty sure \x is used for string representations, while 0x is for hexadecimal nums

clear venture
#

^

#

hexadecimal literals can be defined with 0x

dusk breach
quartz wave
fleet bridge
#

It is always having problems

dense mango
#

!e

global_var = 3

class Animal():
  def foo(self):
    return global_var
  def bar(self):
    return dict

anim = Animal()
print(anim.foo())
print(anim.bar())
night quarryBOT
#

@dense mango :white_check_mark: Your 3.11 eval job has completed with return code 0.

001 | 3
002 | <class 'dict'>
dense mango
#

All I've done here is change some names, the structure is identical.

#

It's just that Python has some surprising rules about renaming stuff that starts with a __ in class scope.

#

It has nothing to do with the type system

#

When you type __example inside a class MyClass: ..., Python sees __MyClass_example

#

So there just happens to be a global (module-level) variable with that name

fleet bridge
#

Attribute lookups are inconsistent for types and non-types.
Suppose X is a class and x is an instance of X, and X.a is some descriptor object in X dict. Both X.a and x.a will execute descriptor protocol, but x.b will not (assuming it is a descriptor object in instance dict)

#

I expect X.a and x.b to behave in the same way

dense mango
#

There's no attribute lookup involved in that example. The only attribute lookup is the method calls.

fleet bridge
#

it is not related to your example, it is just my thoughts

dense mango
#

__Animal_type and type are not attributes of Animal

#

Oh my mistake, I thought you were replying to me

fleet bridge
#

I'm sorry that i interrupted you

#

Name mangling is also inconsistent

#

!e ```py
class X: __a=1
class X: __a=1
class _X: __a=1
print(vars(X))
print(vars(X))
print(vars(_X))

night quarryBOT
#

@fleet bridge :white_check_mark: Your 3.11 eval job has completed with return code 0.

001 | {'__module__': '__main__', '_X__a': 1, '__dict__': <attribute '__dict__' of 'X' objects>, '__weakref__': <attribute '__weakref__' of 'X' objects>, '__doc__': None}
002 | {'__module__': '__main__', '_X___a': 1, '__dict__': <attribute '__dict__' of '_X_' objects>, '__weakref__': <attribute '__weakref__' of '_X_' objects>, '__doc__': None}
003 | {'__module__': '__main__', '_X__a': 1, '__dict__': <attribute '__dict__' of '_X' objects>, '__weakref__': <attribute '__weakref__' of '_X' objects>, '__doc__': None}
fleet bridge
dense mango
#

Yep

fleet bridge
#

Because it lstrip's underscores from class name

dense mango
#

I think it would be nice if descriptors worked the same when the descriptor is in the class dict vs the instance dict.

fleet bridge
#

!e ```py
x=type('',(),dict(init=lambda self:setattr(self,'dict',globals())))()
print(x.x is x)
a = 1
x.b = 2
print(x.a + b)

night quarryBOT
#

@fleet bridge :white_check_mark: Your 3.11 eval job has completed with return code 0.

001 | True
002 | 3
fleet bridge
#

Here x is an object that provides convenient way to use global vars through attributes on x.
Idk if it is useful, but it is definitely interesting

#

!e ```py
X=type('',(dict,),dict(init=lambda self,*a,**b:setattr(self,'dict',self)))
x = X(a=1, b=2)
print(x)
x[3] = x['a'] + x.b
print(x)

#

Sadly dict initialization is broken here

#

!e ```py
X=type('',(dict,),dict(init=lambda self,*a,**b:[setattr(self,'dict',self),dict.init(self,*a,**b)][0]))
x = X(a=1, b=2)
print(x)
x[3] = x['a'] + x.b
print(x)

night quarryBOT
#

@fleet bridge :white_check_mark: Your 3.11 eval job has completed with return code 0.

001 | {'a': 1, 'b': 2}
002 | {'a': 1, 'b': 2, 3: 3}
fleet bridge
#

Yay

#

Nice

restive void
#

!e copying from ot0: Lifetimes in Python!

import sys
import threading
from time import sleep
from typing import Annotated, get_origin, get_args
from collections import namedtuple

timeout = namedtuple("timeout", "s")
def deleter(seconds, name, scope):
    sleep(seconds)
    exec(f"del {name}", scope.f_globals, scope.f_locals)
class A:
    def __init__(self):
        self.d = {}
    def __setitem__(self, name, val):
        origin = get_origin(val)
        if origin is Annotated:
            *_, deadline = get_args(val)
            if isinstance(deadline, timeout):
                frame = sys._getframe(1)
                threading.Thread(
                    target=deleter,
                    args=(deadline.s, name, frame)
                ).start()
        self.d[name] = val

    def __getitem__(self, item):
        return self.d[item]

__annotations__ = A()

x: Annotated[int, timeout(1)] = 23
print(x)
sleep(2)
print(x)
night quarryBOT
#

@restive void :x: Your 3.11 eval job has completed with return code 1.

001 | 23
002 | Traceback (most recent call last):
003 |   File "/home/main.py", line 34, in <module>
004 |     print(x)
005 |           ^
006 | NameError: name 'x' is not defined
hollow vigil
#

I just wrote this one-line image to ascii text converter:

(lambda u,r,n:(lambda i,k:(lambda j:[print("".join([" ░▒▓█"[int((1-j.getpixel((x,y))/255)*4)]for x in r(k*2)]))for y in r(k)])(i.open(u("sys").argv[1]).convert("L").resize((k*2,k),1)))(u("PIL.Image",n,n,("PIL")),u("os").get_terminal_size().lines))(__import__,range,None)

what do you guys think?

wheat river
#

!e

import ast

with open(__file__) as source_file:
    source = iter(ast.parse(source_file.read()).body)


def givex():
    for node in source:
        if isinstance(node, ast.Assign):
            if node.value.func.id != "givex":
                continue
            if not isinstance(node.targets[0], ast.Tuple):
                continue

            return range(len(node.targets[0].elts))

    return (0,)


a, b = givex()
c, d, e, f = givex()

print(a, b)
print(c, d, e, f)
night quarryBOT
#

@wheat river :white_check_mark: Your 3.11 eval job has completed with return code 0.

001 | 0 1
002 | 0 1 2 3
languid hare
#

wouldnt it be return 0 at the end

#

since x, = givex() would be covered by the tuple case

#

otherwise x = givex() would be x = (0,)

wheat river
#

Yea ur right

sullen cargo
#

Ohhhhhhhhhhhhh. "PIL"

#

I need to look into that. I've always wanted to do that.

#

The closest I got to messing with graphics is using features in pygame.

#

Nice work.

quartz wave
#

ideas for cpython

unique heath
#

make faster

quartz wave
#

n easily

unique heath
#

make slower

quartz wave
#

no

fleet bridge
# quartz wave ideas for cpython

make reprs better, so they more frequently return same value when eval'ed:

# functions/lambdas:
>>> f = lambda x: lambda y: x + y
>>> f(1)
<lambda <lambda>@<lambda> x=1>
>>> f
<lambda>
>>>
>>> def g(x):
...   def h(y):
...     return x + y
...   return h
...
>>> g
g
>>> g(1)
<function g@h x=1>

# methods/bound methods:
>>> list.append
list.append
>>> [].append
[].append
>>> {1:2}.keys.__call__
{1: 2}.keys.__call__

# descriptors:
>>> object.__dict__['__class__']
<slot object.__class__>
>>> type.__dict__['__bases__']
<slot type.__bases__>

# modules:
>>> import math; math
math
>>> import os.path
>>> os.path
ntpath

# types/instances:
>>> int
int
>>> class Meta(type): ...
...
>>> class X(metaclass=Meta): ...
...
>>> X
<Meta 'X'>
>>> X()
<<Meta 'X'> at 0x001A1ECC61A50>
>>>
>>> class Y: ...
...
>>> Y
Y
>>> Y()
<Y at 0x001A1ECD88690>

# properties/classmethods/staticmethods:
>>> @property
... def x(): ...
...
>>> @x.setter
... def x(): ...
...
>>> @x.deleter
... def x(): ...
...
>>> x
property(fget=x, fset=x, fdel=x)
>>>
>>> classmethod(lambda: ...)
classmethod(<lambda>)
unique heath
unique heath
fleet bridge
#
>>> object.__dict__
mappingproxy({   '__new__': object.__new__,
                 '__repr__': sitecustomize._@__repr__,
                 '__hash__': object.__hash__,
                 '__str__': object.__str__,
                 '__getattribute__': object.__getattribute__,
                 '__setattr__': object.__setattr__,
                 '__delattr__': object.__delattr__,
                 '__lt__': object.__lt__,
                 '__le__': object.__le__,
                 '__eq__': object.__eq__,
                 '__ne__': object.__ne__,
                 '__gt__': object.__gt__,
                 '__ge__': object.__ge__,
                 '__init__': object.__init__,
                 '__reduce_ex__': object.__reduce_ex__,
                 '__reduce__': object.__reduce__,
                 '__getstate__': object.__getstate__,
                 '__subclasshook__': object.__subclasshook__,
                 '__init_subclass__': object.__init_subclass__,
                 '__format__': object.__format__,
                 '__sizeof__': object.__sizeof__,
                 '__dir__': object.__dir__,
                 '__class__': <slot object.__class__>,
                 '__doc__': 'The base class of the class hierarchy.\n'
                            '\n'
                            'When called, it accepts no arguments and returns a new featureless\n'
                            'instance that has no instance attributes and cannot be given any.\n'})
fleet bridge
unique heath
#

this isnt html tho dude

fleet bridge
fleet bridge
quartz wave
#

yea

fleet bridge
#

!paste

night quarryBOT
#
Pasting large amounts of code

If your code is too long to fit in a codeblock in Discord, you can paste your code here:
https://paste.pythondiscord.com/

After pasting your code, save it by clicking the Paste! button in the bottom left, or by pressing CTRL + S. After doing that, you will be navigated to the new paste's page. Copy the URL and post it here so others can see it.

fleet bridge
#

also do this in your cpython fork: ```py
del builtins.quit
del builtins.exit
del builtins.copyright
del builtins.credits
del builtins.license

#

these things are very anoying

quartz wave
#

why

fleet bridge
#

because of this mess ```py

builtins.dict
{ 'name': 'builtins',
...,
'open': io.open,
'quit': Use quit() or Ctrl-Z plus Return to exit,
'exit': Use exit() or Ctrl-Z plus Return to exit,
'copyright': Copyright (c) 2001-2022 Python Software Foundation.
All Rights Reserved.

Copyright (c) 2000 BeOpen.com.
All Rights Reserved.

Copyright (c) 1995-2001 Corporation for National Research Initiatives.
All Rights Reserved.

Copyright (c) 1991-1995 Stichting Mathematisch Centrum, Amsterdam.
All Rights Reserved.,
'credits': Thanks to CWI, CNRI, BeOpen.com, Zope Corporation and a cast of thousands
for supporting Python development. See www.python.org for more information.,
'license': Type license() to see the full license text,
'help': Type help() for interactive help, or help(object) for help about object.}

fleet bridge
#

x? syntax for repl is pretty cool
it runs help(x)

>>> int?
Help on class int in module builtins:

class int(object)
 |  int([x]) -> integer
 |  int(x, base=10) -> integer
...
#

(in my repl it also works if i type >>> ?i???n????????????t?)

fleet bridge
#

@quartz wave can your inline module inline functions?

#

my old 3.10 impl couldnt do it

#

i have 3.11 code that can do that

quartz wave
hasty temple
#

e.g.

items = [
  (partition[0], partition[2])
  for item in list_of_strings
  where partition = item.partition('.')
]
proper vault
#

for partition in [item.partition('.')]

hasty temple
#

well yeah obviously there's other ways to do it

proper vault
#

it would be neat to have though

#

everytime you write for a in [b], you are making your code more incomprehensible

quartz wave
#

i might just make where a = x equivalent to for a in [x]

proper vault
#

on that note, I read for a in [b] is optimised into a normal assignment, is that actually a thing?

quartz wave
quartz wave
#

i'm gonna continue development on monday since i can't use the pc on sundays

fleet bridge
#

Do you want my function inlining code? (It is awful, as usual)

#

Implement tagged breaks/continues in your cpython
(And optionally goto)

versed eagle
#

goto would be nice

fleet bridge
#

Implement goto from one function to another

#

Also consider creating some object for ecery target. And we should be able to get this object, pass it to goto statement and jump to place where goto object was defined

#
def f():
  label a
  print("a")
  return
  label b
  print("b")

print(f.a) # <goto to file "..." at line 123>

goto f.a # jumls to label a in f, prints a

goto [f.a, f.b][random.randint(0,1)] # haha

fleet bridge
#

Make return and raise not statements, but expressions syntactically. They doesn't return anything because it doesn't make sense, but you can use them in expressions.

#

And assert too*

meager zinc
#

we need manual memory management

fleet bridge
#
while True:
    malloc(1)
#

Cursed

versed eagle
#
while malloc(1):
    ...
meager zinc
#

what if python made the gc async

fleet bridge
#

!e ```py
def f():
try:f()
except:f()
f()

night quarryBOT
#

@fleet bridge :warning: Your 3.11 eval job timed out or ran out of memory.

[No output]
fleet bridge
#

This this should crash

fleet bridge
meager zinc
#

😮

#

genius

fleet bridge
#
await print('hello world')
#

Wait no

#
await print(await 'hello world')
#

Fixed

#

Wait no

#
await (await print)(await 'hello world')
#

Fixed

astral rover
#

why arent you awaiting the await smh?

fleet bridge
#

Because it is keyword

#

Imagine async compilation

dreamy pier
#
await async await def await function(await a, await b):
    ...
unreal echo
#

Bruh had to change

#

Had to make it support stuff like tuple[int|str]|list[list]]

#

Also why is typing.Optional like 3 different types in different scenarios

versed eagle
#

what does it do when it gets multiple overloads that are possible?

#

ooo you have like a scoring system to check how closely it matches the desired type

unreal echo
#

I thought about making it prefer more strict arguments, but that wouldnt make sense

#

Since the user would be responsible for making different functions, why make two functions that have the same argument types even for overloading?

versed eagle
#

but if the user passes an int, they probably want it to use the int one

versed eagle
quartz wave
quartz wave
# fleet bridge make reprs better, so they more frequently return same value when eval'ed: ```py...

2nd one partially implemented ```pycon

.\cpython-main\PCbuild\amd64\python.exe
Python 3.13.0a0 (heads/main-dirty:ef67ea5, Aug 19 2023, 22:20:40) [MSC v.1937 64 bit (AMD64)] on win32
Type "help", "copyright", "credits" or "license" for more information.

[].append
[].append
list.append
<method 'append' of 'list' objects>
min.call
min.call
[].getitem
[].getitem
{1: 2}.keys
{1: 2}.keys
{1: 2}.keys.call
{1: 2}.keys.call

fleet bridge
#

nice

quartz wave
# fleet bridge make reprs better, so they more frequently return same value when eval'ed: ```py...

2nd one fully implemented, 3rd one fully implemented, 4th one fully implemented, 5th one partially implemented ```pycon

.\cpython-main\PCbuild\amd64\python.exe
Python 3.13.0a0 (heads/main-dirty:ef67ea5, Aug 19 2023, 22:20:40) [MSC v.1937 64 bit (AMD64)] on win32
Type "help", "copyright", "credits" or "license" for more information.

list.append
list.append
object.dict['class']
<slot object.class>
type.dict['bases']
<slot type.bases>
import math; math
math
import os.path
os.path
ntpath
int
int
class Meta(type): ...
...
class X(metaclass=Meta): ...
...
X
<Meta 'X'>
X()
<<Meta 'X'> at 0x00000258CA58BE60>
class Y: ...
...
Y
Y
Y()
<Y at 0x00000258CA58BE60>
classmethod(lambda: ...)
classmethod(<lambda>)

quartz wave
# fleet bridge make reprs better, so they more frequently return same value when eval'ed: ```py...

5th one fully implemented ```pycon

.\cpython-main\PCbuild\amd64\python.exe
Python 3.13.0a0 (heads/main-dirty:ef67ea5, Aug 19 2023, 22:20:40) [MSC v.1937 64 bit (AMD64)] on win32
Type "help", "copyright", "credits" or "license" for more information.

@property
... def x(): ...
...
@x.setter
... def x(): ...
...
@x.deleter
... def x(): ...
...
x
property(fget=x, fset=x, fdel=x)
classmethod(lambda: ...)
classmethod(<lambda>)
class A(classmethod): ...
...
A(lambda: ...)
A(<lambda>)

#
  • additional in the file ```pycon

.\cpython-main\PCbuild\amd64\python.exe
Python 3.13.0a0 (heads/main-dirty:ef67ea5, Aug 19 2023, 22:20:40) [MSC v.1937 64 bit (AMD64)] on win32
Type "help", "copyright", "credits" or "license" for more information.

import struct
struct.Struct('d')
_struct.Struct(b'd')

quartz wave
rugged sparrow
#

im trying to write that rn

quartz wave
#

especially doing that with the current goto implementation i have rn

quartz wave
#

i'm gonna do frozendict

rugged sparrow
# quartz wave in fact really difficult

My idea for implementation is using sys.settrace to basically do a delayed jump and watch until execution is inside of the target function, then call the target function yourself after setting whatever global signals what the trace function should look for

quartz wave
#

my problem is i already have a working goto implementation

#

and the names are separate from variable names so things like these are possible ```py
a = 5
label a
a *= 2
if a < 100:
goto a
print(a)

#

and they translate into jumps and jump offsets instead of objects/instructions

rugged sparrow
#

Ah mine is a native version, so labels and jumps look like label .a and goto .func.label

versed eagle
#

since type is the metaclass

quartz wave
quartz wave
fleet bridge
quartz wave
fleet bridge
#

So it is just an intermediate assignment statement

#

Cool

fleet bridge
lament pond
#

just a calculator: for vars in [[int(input("Number 1: ")),input("+, -, * or /? "),int(input("Number 2: "))]]: print(vars[0]+vars[2] if vars[1] == "+" else vars[0]-vars[2] if vars[1] == "-" else vars[0]*vars[2] if vars[1] == "*" else vars[0]/vars[2] if vars[1] == "/" else print('Error'))

quartz wave
lament pond
lament pond
#
Number 1: 6
+, -, * or /? -
Number 2: 7
42
quartz wave
#

eh

#

i'll fix it a second time

#

done

lament pond
quartz wave
#

fixed it a 3rd time

lament pond
#
Number 1: 1
+, -, * or /? /
Number 2: 0
Traceback (most recent call last):
ZeroDivisionError: division by zero
quartz wave
#

works fine

lament pond
# quartz wave works fine
Number 1: 5.5
Traceback (most recent call last):
ValueError: invalid literal for int() with base 10: '5.5'
quartz wave
#

works just like the original

lament pond
#

oh, if thats what you are comparing it to

#

gimme a sec

stark granite
stark granite
#

:D

lament pond
#

squeezed into 1 line

stark granite
#

i think i might be able to do better?

#

idk

lament pond
stark granite
#

actually i doubt..?

lament pond
stark granite
lament pond
lament pond
stark granite
#

quite an interesting task

quartz wave
#

are you sure?

stark granite
quartz wave
#

i'll cook up a challenge then

stark granite
lament pond
quartz wave
#
import pygame as pg
import pygame.locals
import sys # bonus! for exit purposes
from random import randint as ri

sc = pg.display.set_mode((600, 600))
cl = pg.time.Clock()
sp = pg.Vector2(10, 10)
sb = []
di = pg.Vector2(10, 0)

def nf():
    global fo
    fo = pg.Vector2(ri(0, 59) * 10, ri(0, 59) * 10)

while True:
    sb.append(pg.Vector2(sp))
    sb.pop(0)
    sp += di
    if sp in sb or not (0 <= sp.x <= 600 and 0 <= sp.y <= 600):
        sb.clear()
        sp.update(10, 10)
    if sp == fo:
        sb.insert(0, pg.Vector2(-10, -10))
        nf()
    sc.fill((0, 0, 0))
    pg.draw.rect(sc, (255, 0, 0), (fo.x, fo.y, 10, 10))
    pg.draw.rect(sc, (255, 255, 255), (sp.x, sp.y, 10, 10))
    for p in sb:
        pg.draw.rect(sc, (255, 255, 255), (p.x, p.y, 10, 10))
    for ev in pg.event.get():
        if ev.type == pg.locals.QUIT:
            sys.exit(0) # 1 / 0
        elif ev.type == pg.locals.KEYDOWN:
            if ev.key == pg.locals.K_w: di.update(0, -10)
            elif ev.key == pg.locals.K_s: di.update(0, 10)
            elif ev.key == pg.locals.K_a: di.update(-10, 0)
            elif ev.key == pg.locals.K_d: di.update(10, 0)
    pg.display.update()
    cl.tick(10)
lament pond
# quartz wave i reverse-one-linered that i think

this one? ```py
(pg:=import("pygame"),import("pygame.locals"),ri:=import("random").randint,sc:=pg.display.set_mode((600, 600)),cl:=pg.time.Clock(),sp:=pg.Vector2(10,10),sb:=[],di:=pg.Vector2(10,0),nf:=lambda:globals().update(fo=pg.Vector2(ri(0,59)*10,ri(0,59)*10)),nf(),[(sb.append(pg.Vector2(sp)),sb.pop(0),sp.iadd(di),(sb.clear(),sp.update(10,10))if(sp in sb or not(0<=sp.x<=600and 0<=sp.y<=600))else None,(sb.insert(0,pg.Vector2(-10,-10)),nf())if sp==fo else None,sc.fill((0,0,0)),pg.draw.rect(sc,(255,0,0),(fo.x,fo.y,10,10)),pg.draw.rect(sc,(255,255,255),(sp.x,sp.y,10,10)),[pg.draw.rect(sc,(255,255,255),(p.x,p.y,10,10))for p in sb],[((1/0)if ev.type==pg.locals.QUIT else di.update({pg.locals.K_w:(0,-10),pg.locals.K_s:(0,10),pg.locals.K_a:(-10,0),pg.locals.K_d:(10,0)}.get(ev.key,di))if ev.type==pg.locals.KEYDOWN else None)for ev in pg.event.get()],pg.display.update(),cl.tick(10),)for _ in iter(int,1)])

quartz wave
# stark granite lol
__builtins__.__getattribute__((_:=__name__.__class__.__class__.__doc__.__getitem__((___:=(_:=__name__.__getitem__((__:=__name__.__class__().__len__()))).__add__(_).__len__())).__add__((_____:=(_____:=__name__.__ne__(__name__).__invert__()).__neg__().__truediv__(_____.__add__(_____).__neg__()).__rpow__(_____).__class__).__doc__.__getitem__((______:=__name__.__eq__(__name__).__pos__()))).__add__(__name__.__len__().__class__.__doc__.__getitem__(__)).__add__(__name__.__len__().__class__.__doc__.__getitem__(______)).__add__(__name__.__class__.__class__.__doc__.__getitem__(__))))(___________ if(___________:=(________:=__builtins__.__getattribute__((_______:=__name__.__len__().__class__.__doc__.__getitem__(__).__add__(__name__.__len__().__class__.__doc__.__getitem__(______)).__add__(__name__.__class__.__class__.__doc__.__getitem__(___)).__add__(__name__.__len__().__class__.__module__.__getitem__(______)).__add__(__name__.__class__.__class__.__doc__.__getitem__(__))))()).__mul__(__________:=__builtins__.__getattribute__((_________:=__name__.__len__().__class__.__doc__.__getitem__(__).__add__(__name__.__len__().__class__.__doc__.__getitem__(______)).__add__(__name__.__class__.__class__.__doc__.__getitem__(__))))(__builtins__.__getattribute__(_______)())))!=(_________________:=__builtins__.__getattribute__(__builtins__.__dir__().__getitem__((____________:=(_____________:=(____________:=__name__.__getitem__(__)).__add__(____________).__add__(____________).__len__()).__mul__((________________:=(______________:=___.__mul__(___)).__mul__(_____________).__add__((_______________:=___.__mul__(___).__invert__().__neg__()))))))))else __________.__rmul__(________))
#

try that

quartz wave
#

try testing it

stark granite
stark granite
#

it did nothing?

quartz wave
#

it should be pretty quick once you figure it out

stark granite
#

is it a calculator?

quartz wave
stark granite
lament pond
#

I like vivax, cool friend

stark granite
#

tho i doubt

#

uh

#

oh

#

ic

#

basically this: input() * int(input())?

quartz wave
stark granite
#

ah

#

print(input() * int(input()))

quartz wave
#

yep

stark granite
#

why tf does it need __doc__ and __len__ and __rmul__ (just as well __add__)?

#

wait i gotta understand wtf does it do

fallow leaf
#

Does this count as esoteric ```py
def inject(clazz, otherclazz=None):
if otherclazz==None:
for name, obj in globals().copy().items():
if isinstance(obj, type) and not issubclass(obj, clazz):
try:
for method in getMethods(clazz):
setattr(obj, method, getattr(clazz,method))
for variable in getVariables(clazz):
setattr(obj, variable, getattr(clazz,variable))
globals()[name] = obj
print(obj.name)
except Exception as e:
print(e)
else:
obj = globals()[otherclass.name]
for method in getMethods(clazz):
setattr(obj, method, getattr(clazz,method))
for variable in getVariables(clazz):
setattr(obj, variable, getattr(clazz,variable))
globals()[otherclass.name] = obj

#

Because I doubt alot of people would understand it 😂

fallow leaf
gentle plover
restive void
quartz wave
fallow leaf
#

Mines is somewhat readable still, but that is on a whole other level 💀

quartz wave
#

321 ```py
def a(c,o):
for v in dir(c):
if v not in dir(type)and(callable(x:=getattr(c,v))or"weakref"!=v):setattr(o,v,x)
def inject(c,o):
if o==None:
for x in globals().values():
if isinstance(x,type)&~issubclass(x,c):
try:a(c,x),print(x.name)
except Exception as e:print(e)
else:a(c,globals()[o.name])

#

309 ```py
def a(c,o):
for v in{*dir(c)}-{*dir(type)}:
if callable(x:=getattr(c,v))or"weakref"!=v:setattr(o,v,x)
def inject(c,o,g=globals()):
if o==None:
for x in g.values():
if isinstance(x,type)&~issubclass(x,c):
try:a(c,x),print(x.name)
except Exception as e:print(e)
else:a(c,g[o.name])

fallow leaf
#

What are you using to do this?

quartz wave
#

306 might continue tmr ```py
def a(c,o):
for v in{*dir(c)}-{*dir(type)}:
if callable(x:=getattr(c,v))or"weakref"!=v:setattr(o,v,x)
def inject(c,o,g=globals()):
if o==None:
for x in g:
if isinstance(x:=g[x],type)&~issubclass(x,c):
try:a(c,x),print(x.name)
except Exception as e:print(e)
else:a(c,g[o.name])

stark granite
restive void
#

This is not exactly idiomatic code anyways

stark granite
#

actually what is the reason behind using is instead of ==?

languid hare
#

!e

import numpy as np
x = np.array([1, 2, 3])

print(x is None)
print(None == x)
print(x == None)
night quarryBOT
#

@languid hare :white_check_mark: Your 3.11 eval job has completed with return code 0.

001 | False
002 | [False False False]
003 | [False False False]
languid hare
#

there is no guarantee the == works how you expect it to
of course, for builtins they're much more well behaved, but you shouldn't rely on it

rugged sparrow
#

@fleet bridge native goto that can jump into a new function scope

#

it uses sys.settrace

fleet bridge
#

Yooo

#

Nice

rugged sparrow
#

basically just sets a trace function to perform the jump as soon as execution enters a frame with a specific code object, then calls the function

fleet bridge
#

That's smart

rugged sparrow
#

rn the function jump doesnt share a its jump code with the normal goto code, im trying to generalize rn

rugged sparrow
versed eagle
quartz wave
versed eagle
#

297

#
def a(c,o):[setattr(o,v,x)for v in{*dir(c)}-{*dir(type)}if callable(x:=getattr(c,v))or"__weakref__"!=v]
def inject(c,o,g=vars()):
 if o!=None:return a(c,g[o.__name__])
 for x in g:
  if isinstance(x:=g[x],type)&~issubclass(x,c):
   try:a(c,x),print(x.__name__)
   except Exception as e:print(e)```
#

294

versed eagle
#

292, if you assume .__weakref__ will never be callable (which is almost always a reasonable assumption)

def a(c,o):[setattr(o,v,x)for v in{*dir(c)}-{*dir(type)}-{"__weakref__"}if callable(x:=getattr(c,v))]
def inject(c,o,g=vars()):
 if o!=None:return a(c,g[o.__name__])
 for x in g:
  if isinstance(x:=g[x],type)&~issubclass(x,c):
   try:a(c,x),print(x.__name__)
   except Exception as e:print(e)```
#

thats all i can think of for now

#

might try to make it shorter tomorrow

#

wait actually

#
def a(c,o):[setattr(o,v,x)for v in{*dir(c)}-{*dir(type),"__weakref__"}if callable(x:=getattr(c,v))]
def inject(c,o,g=vars()):
 if o!=None:return a(c,g[o.__name__])
 for x in g:
  if isinstance(x:=g[x],type)&~issubclass(x,c):
   try:a(c,x),print(x.__name__)
   except Exception as e:print(e)```
#

290

#

ok now im done for today

#

no more ideas

quartz wave
#

it's either callable or not callable and is not .__weakref__

versed eagle
#

oh true

#

im too tired for this lmao

quartz wave
#

so 273 ```py
def a(c,o):[setattr(o,v,getattr(c,v))for v in{*dir(c)}-{*dir(type),"weakref"}]
def inject(c,o,g=vars()):
if o!=None:return a(c,g[o.name])
for x in g:
if isinstance(x:=g[x],type)&~issubclass(x,c):
try:a(c,x),print(x.name)
except Exception as e:print(e)

versed eagle
#

#

i should probably go sleep now

quartz wave
#

ok gn

versed eagle
#

gn

quartz wave
#

can use exec() for a possible improvement

#

268 ```py
def inject(c,o,g=vars()):
def a(o):[setattr(o,v,getattr(c,v))for v in{*dir(c)}-{*dir(type),"weakref"}]
if o!=None:return a(g[o.name])
for x in g:
if isinstance(x:=g[x],type)&~issubclass(x,c):
try:a(x),print(x.name)
except Exception as e:print(e)

#

266 ```py
def inject(c,o,g=vars()):
def a(o):[setattr(o,v,getattr(c,v))for v in{*dir(c)}-{*dir(type),"weakref"}]
if o!=None:a(g[o.name]);g=[]
for x in g:
if isinstance(x:=g[x],type)&~issubclass(x,c):
try:a(x),print(x.name)
except Exception as e:print(e)

compact raven
#

I hardly ever use is, except for testing/debugging.

stark granite
unique heath
rugged sparrow
#

Like jump into a context manager block?

rugged sparrow
#

You could implement that by jumping to the beginning of the setup line, then installing a handler to jump to the specific label inside the ctx manager block as soon as execution enters the block

earnest wing
#

Hah, that's some gimped goto

rugged sparrow
#

had to still execute the ctx manager to maintain stack levels, but was able to jump around upon entry

restive void
# rugged sparrow

Eh, that's way too well-behaved... Where's the fun if it actually sets up the resource :D

#

Trace functions don't let you jump into a context manager though, right?

rugged sparrow
#

they technically dont

#

but my implementation uses trace functions

restive void
#

Yeah, you jump in front of it, and then immediately jump within it, right?

rugged sparrow
#

yup

#

but i implemented it in such a way that also allows jumps into and out of for loops

restive void
#

(Reminds me of the weird hack I had to pull with dont)

#

Nice, I'm always impressed by your stunts :)

earnest wing
#

I like the oxymoron of a resource respecting goto

rugged sparrow
restive void
#

Do you set up/tear down the trace function stuff before and after each jump?

rugged sparrow
#

yea

proper vault
#

Jumping out of a with block will skip it's exit, right?

rugged sparrow
#

not currently

#

actually yes it does

#

unintentionally

restive void
#

Alternative syntax idea:

goto(my_label)

my_label:  # (half-width hangul filler)
#

Ah, I guess goto(my_label) doesn't work if the tf isn't active yet (unless the label has been declared already). And it would make it more complicated inside functions.. too bad

rugged sparrow
#

yea, i played around with a few syntaxes, and keyword .label was the easiest one to scan bytecode for (LOAD_NAME | LOAD_GLOBAL + LOAD_ATTR)

restive void
#

The label I think is doable now that I think about it. It's just a SETUP_ANNOTATIONS at the beginning, and then somewhere a LOAD_NAME, LOAD_NAME ("__annotations__"), LOAD_CONST, STORE_SUBSCR.

#

And technically the goto(my_label) is also doable by hooking into globals/builtins __missing__ (or equivalent).

rugged sparrow
#

the issue is it gets stripped away inside functions

#

!e ```py
import dis
def foo():
label: here

dis.dis(foo)```

night quarryBOT
#

@rugged sparrow :white_check_mark: Your 3.11 eval job has completed with return code 0.

001 |   2           0 RESUME                   0
002 |               2 LOAD_CONST               0 (None)
003 |               4 RETURN_VALUE
serene stratus
#

Even if you turn off all optimizations?

rugged sparrow
#

im pretty sure they are always stripped

rugged sparrow
restive void
#

goto &function.args(...).label?

#

Or just goto &function(...).label?

rugged sparrow
#

it would work for goto .function(...).label but would not for goto *function(...).label (which is my syntax for dynamic jumps)

fallow leaf
#

How would I modify on a part of a built-in classes methods body

#

Or any classes methods body

#

Cant find anything for this anywhere

dull tusk
#

Can't you just create a new type that inherits from builin one?

rugged sparrow
night quarryBOT
#

@rugged sparrow :white_check_mark: Your 3.11 eval job has completed with return code 0.

[2, 3]
fallow leaf
#

Exactly💀

#

But I wouldn't want to rewrite the entire body only part of it like changing the bytecode of the return value etc

rugged sparrow
#

can you show me a psudocode example?

dull tusk
#

i belive you can override any method you want like that, but I have not tested it:
MyClass.my_method = lambda self: completely_different_function()

rugged sparrow
#

you can do that for classes defined in python, not classes defined in C
fishhook lets you do it for C classes as well

fallow leaf
#

Original```
class myClass:
def say(self,d):
print(d)
if d == 10:
return "yes"
else:
return "no"

Modified 

class myClass:
def say(self,d):
print(d)
if d == 10:
return 10 <- changed value and not the whole body
else:
return "no"

rugged sparrow
#

^ in that specific example, you could swap out the constant value "yes" with 10

fallow leaf
#

Can you give me a example?

rugged sparrow
#

!e ```py
class myClass:
def say(self,d):
print(d)
if d == 10:
return "yes"
else:
return "no"

orig_consts = list(myClass.say.code.co_consts)
orig_consts[orig_consts.index("yes")] = 10
myClass.say.code = myClass.say.code.replace(co_consts=tuple(orig_consts))

m = myClass()
print(m.say(10))```

night quarryBOT
#

@rugged sparrow :white_check_mark: Your 3.11 eval job has completed with return code 0.

001 | 10
002 | 10
fallow leaf
#

.code is a thing? 💀 that's so much easier than what I was thinking

#

But does it work for built-in classes?

fleet bridge
#

!e ```py
class X:
def foo(self):
print('foo')

from fishhook import hook
@hook(X)
def foo(self):
print('bar')

X().foo()

night quarryBOT
#

@fleet bridge :white_check_mark: Your 3.11 eval job has completed with return code 0.

bar
fleet bridge
#

cool

#

fishhook can even patch non-C classes

rugged sparrow
rugged sparrow
#

tbh i don't remember if i tested orig with python classes

fallow leaf
fleet bridge
#

!e ```py
class X:
def foo(self):
print('foo')

from fishhook import hook, orig
@hook(X)
def foo(self):
print('bar')
orig(self)

X().foo()

night quarryBOT
#

@fleet bridge :white_check_mark: Your 3.11 eval job has completed with return code 0.

001 | bar
002 | foo
fleet bridge
#

cool

fleet bridge
rugged sparrow
#

sweet

rugged sparrow
fallow leaf
#

Yes

#

Minecraft like mixins, @mixin(target, etc)

rugged sparrow
#

seems every few months or so someone is in here trying to write python mixins lol

#

i have an implementation for 3.10 somewhere

fallow leaf
#

Nah I am really gonna do it

rugged sparrow
#

but so much changes with the bytecode every version it is very difficult to handle every situation

#

and mixins for builtin classes, do you mean like assembly patching?

fallow leaf
#

Possibly

rugged sparrow
#

ah yea, that stuff gets very finiky very fast

#

i am working on fishhook.asm currently to make assembly patching way easier, (currently it only supports complete hooking of C functions on x86 intel)

fleet bridge
#

is there any fishhook documentation?
i would like to see examples of how to use fishhook.asm.hook

rugged sparrow
fleet bridge
#

can you just drop some examples somewhere?

rugged sparrow
#

!e ```py
from ctypes import *
from fishhook.asm import hook

@hook(pythonapi.PyDict_SetDefault, restype=py_object, argtypes=[py_object, py_object, py_object])
def setdefault(self, key, value):
if key == 'MAGICVAL':
return self
return pythonapi.PyDict_SetDefault(self, key, value)

pythonapi.PyUnicode_InternFromString.restype = py_object
interned = pythonapi.PyUnicode_InternFromString(b'MAGICVAL')
setdefault.unhook()
print(interned)```

night quarryBOT
#

@rugged sparrow :white_check_mark: Your 3.11 eval job has completed with return code 0.

{'type': 'type', 'AttributeError': 'AttributeError', '__qualname__': '__qualname__', 'obj': 'obj', 'update': 'update', '__dict__': '__dict__', 'getattr': 'getattr', 'setattr': 'setattr', 'hasattr': 'hasattr', '__doc__': '__doc__', '__name__': '__name__', '__module__': '__module__', 'replace': 'replace', 'old': 'old', 'new': 'new', 'sys': 'sys', 'name': 'name', '_DeadlockError': '_DeadlockError', 'waiters': 'waiters', 'count': 'count', 'owner': 'owner', 'wakeup': 'wakeup', 'lock': 'lock', 'allocate_lock': 'allocate_lock', '_thread': '_thread', 'self': 'self', 'add': 'add', 'get': 'get', '_blocking_on': '_blocking_on', 'set': 'set', 'get_ident': 'get_ident', 'seen': 'seen', 'tid': 'tid', 'me': 'me', 'release': 'release', 'acquire': 'acquire', 'has_deadlock': 'has_deadlock', 'RuntimeError': 'RuntimeError', 'id': 'id', 'format': 'format', '__repr__': '__repr__', '__init__': '__init__', '_ModuleLock': '_ModuleLock', '_DummyModuleLock': '_DummyModuleLock', '_lock': '_lock', '_name': '_name',
... (truncated - too long)

Full output: https://paste.pythondiscord.com/DVSANU65G53QEDR4OSQUBBHXZU

rugged sparrow
#

heres an example i made to grab the interned dict

#

it doesnt work with every function, some are optimized in ways that bypass the things it patches

fleet bridge
#

i also would like to see type annotations in fishhook
are they planned in the future?
do you need any help? i think im pretty good at this, i can help you

rugged sparrow
#

honestly, i would love help with that, I have never realy felt the need to add type hints to any of my projects

#

also i really need to write a full docs for fishhook, there are a few features that are not documented at all (like fishhook.asm and @hook(cls1 | cls2))

#

if you want to make pull requests, be my guest, i look thru and merge them

fleet bridge
#

also, which python versions are supported by fishhook?

#

python_requires='>=3.8', i see...

rugged sparrow
#

sure you can run black, and for the typing import i don't have a preference

rugged sparrow
fallow leaf
#

Isn't _code_.co_code the bytecode of the function?

fleet bridge
#

it is

fallow leaf
#

Coul have just told me that 😐

#

Now I can just change the bytecode

fleet bridge
#

i discovered bug in fishhook
if you use same wrapper for two methods with different names, it will overwrite wrong method

#
from fishhook import hook, orig
class X:
    def foo(self):
        print('foo@1')
    def bar(self):
        print('bar@1')

h = hook(X)

@h
def foo(self):
    print('foo@2')
    orig(self)

@h
def bar(self):
    print('bar@2')
    orig(self)


x = X()
x.foo()
print()
x.bar()
rugged sparrow
#

yea that makes sense, the wrapper returned by hook has some internal state stuff

rugged sparrow
rugged sparrow
night quarryBOT
#

fishhook/fishhook.py line 321

name = name or code.co_name```
fleet bridge
#

yes, i know

#

i discovered this bug by looking at this exact line

#

fishhook is actually very hard to type-annotate...

#

especially stuff like @hook.cls

rugged sparrow
#

Yea it has some weird code to facilitate the nicer syntax

#

Working on the better fishhook.asm using keystone and capstone for disassembly and reassembly

fleet bridge
#

im not satisfied with this at all

astral rover
#

whens the mypy plugin happening?

fallow leaf
#
import dis
import types

def my_function(x):
    if x > 0:
        return x * 2
    else:
        return x

original_code = my_function.__code__

new_instructions = []
instructions = list(dis.get_instructions(original_code))
before_instr = None
newopcode = dis.opmap["BUILD_TUPLE"]
for instr in instructions:
    if before_instr is not None and before_instr.opcode == dis.opmap["LOAD_CONST"] and instr.opcode == dis.opmap['RETURN_VALUE']:
        new_instr = dis.Instruction(
            opcode=newopcode,
            opname=dis.opname[newopcode],
            arg=0,
            argval=None,
            argrepr="()",
            offset=instr.offset,
            starts_line=instr.starts_line,
            is_jump_target=instr.is_jump_target
        )
        new_instructions.append(new_instr)
    else:
        new_instructions.append(instr)
    before_instr = instr

modified_code = types.CodeType(
    original_code.co_argcount,
    original_code.co_kwonlyargcount,
    original_code.co_nlocals,
    original_code.co_stacksize,
    original_code.co_flags,
    b''.join(instr.opcode.to_bytes(1,"little") for instr in new_instructions),
    original_code.co_consts,
    original_code.co_names,
    original_code.co_varnames,
    original_code.co_filename,
    original_code.co_name,
    original_code.co_firstlineno,
    original_code.co_lnotab,
    original_code.co_freevars,
    original_code.co_cellvars
)

modified_function = types.FunctionType(modified_code, globals())

result = modified_function(3)
print(result) 
``` don't know what's wrong
#

#bot-commands message

#

^ Error here

#

Thats on 3.11 but on 3.6.6 its Traceback (most recent call last): File "/storage/emulated/0/qpython/projects3/mixins/.last_tmp.py", line 134, in <module> result = modified_function(3) File "/storage/emulated/0/qpython/projects3/mixins/.last_tmp.py", line 80, in my_function if x > 0: IndexError: tuple index out of range

#

This way I can actually append a whole methods body to the instructions

rugged sparrow
#

Ah all of your jump targets are going to need to be recomputed if you are changing the length of the byte code

rugged sparrow
rugged sparrow
#

Oh wait the paste got wiped

versed eagle
#

old pastes do that :(

rugged sparrow
#

I'll go find the source

fleet bridge
rugged sparrow
#

Yea that makes sense, build_orig does a ton of weird stuff to try and ensure it works in any situation

fleet bridge
#

I think annotating only public api (and some easy non-public functions) makes more sense, than annotating everything

#

So the most painful part is hook.* things

fallow leaf
#

At this point I'ma just use fishhook for mixins and use that for the modifying logic

rugged sparrow
#

i found the source but it doesnt even work on 3.10 anymore rip

fallow leaf
#

Alright so when I do something like if x==z: print() that's a jump correct? And the jump target is print correct?

#

Cuz idk

rugged sparrow
#

yea

#

and the jump target in bytecode is going to be an offset

quartz wave
exotic stirrup
#

Guys, I have a question, is it possible to get the media list on the last call of the function when the number of calls is unknown?

import random


media = []


def containing_function():
    media.append('PHOTO')

    print(media)


for _ in range(random.randint(1, 5)):
    containing_function()
quartz wave
quartz wave
# fallow leaf ```py import dis import types def my_function(x): if x > 0: return ...
import dis
import types

def my_function(x):
    if x > 0:
        return x * 2
    else:
        return x

original_code = my_function.__code__

new_instructions = []
instructions = list(dis.get_instructions(original_code))
before_instr = None
newopcode = dis.opmap["BUILD_TUPLE"]
for instr in instructions:
    if before_instr is not None and before_instr.opcode == dis.opmap["LOAD_CONST"] and instr.opcode == dis.opmap['RETURN_VALUE']:
        new_instr = dis.Instruction(
            opcode=newopcode,
            opname=dis.opname[newopcode],
            arg=0,
            argval=None,
            argrepr="()",
            offset=instr.offset,
            starts_line=instr.starts_line,
            is_jump_target=instr.is_jump_target
        )
        new_instructions.append(new_instr)
    new_instructions.append(instr)
    before_instr = instr

modified_code = types.CodeType(
    original_code.co_argcount,
    original_code.co_kwonlyargcount,
    original_code.co_nlocals,
    original_code.co_stacksize,
    original_code.co_flags,
    b''.join(instr.opcode.to_bytes(1,"little")+(instr.arg.to_bytes(1,"little") if instr.arg is not None else b"\0") for instr in new_instructions),
    original_code.co_consts,
    original_code.co_names,
    original_code.co_varnames,
    original_code.co_filename,
    original_code.co_name,
    original_code.co_firstlineno,
    original_code.co_lnotab,
    original_code.co_freevars,
    original_code.co_cellvars
)
``` should work for 3.6 now
fallow leaf
quartz wave
#

tested out the working thing before i changed this part ```diff
new_instructions.append(new_instr)

  • else:
  •    new_instructions.append(instr)
    
  • new_instructions.append(instr)
quartz wave
fallow leaf
quartz wave
# fallow leaf Ok what if I added more than just a different return value? Does that change it?...

here's the modified code from above ```pycon
5 0 LOAD_FAST 0 (x)
2 LOAD_CONST 1 (0)
4 COMPARE_OP 4 (>)
6 POP_JUMP_IF_FALSE 16

6 8 LOAD_FAST 0 (x)
10 LOAD_CONST 2 (2)
12 BINARY_MULTIPLY
14 RETURN_VALUE

8 >> 16 LOAD_FAST 0 (x)
18 RETURN_VALUE
20 LOAD_CONST 0 (None)
22 BUILD_TUPLE 0
24 RETURN_VALUE
``` if the highlighted LOAD_FAST 0 (x) moves from position 16 by instruction addition/removal, the argument to POP_JUMP_IF_FALSE must be changed

quartz wave
fallow leaf
#

()

quartz wave
#

nothing jumps to the final BUILD_TUPLE and RETURN_VALUE

fallow leaf
#

💀

quartz wave
#

which is the only place that contains LOAD_CONST + RETURN_VALUE

fallow leaf
#

Hold on

#

Ohhh the value is before the RETURN_VALUE opcode?

rugged sparrow
#

@fleet bridge a lot of operating systems don't let me map READ/WRITE/EXEC memory anymore, i can only do pairs of READ/WRITE or READ/EXEC. normally that would be fine, but since i have to remap entire memory regions to write in new assembly, sometimes there are functions in the same region that need to get called while the region is not marked executable. (i think im going to have to write my entire mprotect(R/W), writeASM, mprotect(R/X) in assembly

quartz wave
#

i might have to use slightly different syntax to implement dynamic goto/label in cpython

versed eagle
#

are you doing computed goto?

quartz wave
#

jumping in and out of anything that needs init code is hard

rugged sparrow
#

Do you want my source?

rugged sparrow
#

True but it's something to start with right?

quartz wave
#

maybe

#

i might use that after i'm done with the math.factorize() thing

maiden blaze
quartz wave
#

136 -> 116 has an issue ||```py
class Solution:longestCommonPrefix=lambda _,s:s[0][:next((i for i,x in enumerate([*zip(*s),(1,2)])if~-len({*x})),0)]

#

136 -> 112 turns out it was not an issue ||```py
class Solution:longestCommonPrefix=lambda _,s:s[0][:next(i for i,x in enumerate([*zip(*s),(1,2)])if~-len({*x}))]

maiden blaze
#

whats the (1, 2) for

quartz wave
# maiden blaze whats the (1, 2) for

112 -> 110 good point, replaced it with a better one ||```py
class Solution:longestCommonPrefix=lambda _,s:s[0][:next(i for i,x in enumerate([*zip(s),s0])if~-len({*x}))]

#

it's a stopper

maiden blaze
#

[] is shorter than s*0 but i dont get what its for

quartz wave
#

110 -> 108 s*0 -> () + next() -> listcomp[0] ||```py
class Solution:longestCommonPrefix=lambda _,s:s[0][:[i for i,x in enumerate([*zip(*s),()])if~-len({*x})][0]]

quartz wave
maiden blaze
#

what case does it fail for without it

quartz wave
maiden blaze
#

s[0] would fail for that anyway

quartz wave
#

hmm true

maiden blaze
#

oh wait if a single string is empty

quartz wave
#

oh

#

no shared prefix

maiden blaze
#

no ["x", "y"] works without it

#

["x", ""] errors without it

quartz wave
#

hmm yea

maiden blaze
#

["x", "xy"] too

#

dafuq

#

ok ill just accep its necessary

quartz wave
#

i.e. all the other strings start with it

maiden blaze
#

a right

maiden blaze
#

@quartz wave 97

class Solution:longestCommonPrefix=lambda _,s:s[0][:[1==len({*x})for x in[*zip(*s),()]].index(0)]
fleet bridge
#

Cant you:

  1. mark memory as W/E
  2. change code
  3. mark as R/E
  4. execute code
rugged sparrow
#

Can't have a segment be Writeable and Executable at the same time

#

So I'm gonna write my writeASM stub in assembly

fleet bridge
#
  1. mark memory as W
  2. change code
  3. mark as R/E
  4. execute code
#

Fixed

rugged sparrow
#

The problem with doing that in python is that I have to mark an entire 16k page, so if another function is in that page and is called during the patch when the page isn't executable I get a bus error

fleet bridge
#

I see

#

Yeah, doing that in asm now makes sense to me

#

Is it possible to have object that is not an instance of object?

x = ...
assert not isinstance(x, object)
rugged sparrow
#

Via memory tricks you can make a new base type

#

Then I think the resulting objects would not be instances of object

fleet bridge
#
class X(object): ...
x = X()
X.__base__ = X # memory trick requred
assert not isinstance(x, object)
#

Im not sure that this will work

#

Probably you also should modify bases, mro and something else mro-related

#

This will always be funny to me: ```py

class M(type): ...
...
class X(M, metaclass=M): ...
...
X.class = X
X is type(X) is X.class
True
isinstance(X, X)
True
issubclass(X, X)
True

rugged sparrow
#

yea, thats why using direct asm would work

zenith bluff
#

i wonder if it would be possible for lambda to operate on a whole list at once

rugged sparrow
quartz wave
#

84 ```py
minimum_number=m=lambda n:not~-(t:=sum(n))*all(t%i for i in range(2,t))and-~m(n+[1])

#

still 84 but performance boost ```py
minimum_number=m=lambda n:not~-(t:=sum(n))*all(t%i for i in range(2,t))and-~m([t+1])

sick hound
#

how do I join this cult

distant salmon
quartz wave
unique heath
#

whatcha golfing

unique heath
#

wait where r you checking prime

quartz wave
unique heath
#

oh thats the prime check

sick hound
#

/run