Receivers and private methods


#1

how do I make a method of a class private, but yet usable when such class is used as a receiver?


#2

So just so I understand you right you want to do something like this

class Foo {
    someIdentifier fun bar() {}
}

val f = Foo()
with(f) {
    bar()
}
f.bar() // compile error

As far as I know you can’t, not exactly. What you can do is hide some function inside of a special “context”, so that they can only be called from within that context. So you could do something like this:

class Foo{
	var i = 0
		private set

	fun test(){
		inc()    // this is ok, because Foo.inc() is declared in the companion objct
                           // it would not work if Foo.inc() were part of a normal object
	}

	companion object {
		fun Foo.inc(){
			i++
		}
	}
}

val f = Foo()

with(Foo){
	f.inc()
}
with(f){
	inc() // error, we don't know about the functions of the companion here
}

with(Foo){
	with(f){
		inc()  // this works, the with blocks can be switched
	}
}

I’m not sure if this helps you, but it’s all I can think of right now. Also I would consider using 2 with-blocks like that bad style. In general if you have to resort to something like this, it is a signal for a bad code design IMO.
One more thing: you can not stack receivers more then twice, so if you have with(a) { with(b) { with(c) { ... }}} you can no longer access a using this. You can however still use this@label.


#3

Seems quite laborious but yeah I realize i can’t.