Data commit
This commit is contained in:
parent
7387c8f97b
commit
cb5bb5e222
199093 changed files with 3378972 additions and 0 deletions
4
Task/Break-OO-privacy/00-META.yaml
Normal file
4
Task/Break-OO-privacy/00-META.yaml
Normal file
|
|
@ -0,0 +1,4 @@
|
|||
---
|
||||
category:
|
||||
- Object oriented
|
||||
from: http://rosettacode.org/wiki/Break_OO_privacy
|
||||
7
Task/Break-OO-privacy/00-TASK.txt
Normal file
7
Task/Break-OO-privacy/00-TASK.txt
Normal file
|
|
@ -0,0 +1,7 @@
|
|||
Show how to access private or protected members of a class in an object-oriented language from outside an instance of the class, without calling non-private or non-protected members of the class as a proxy.
|
||||
The intent is to show how a debugger, serializer, or other meta-programming tool might access information that is barred by normal access methods to the object but can nevertheless be accessed from within the language by some provided escape hatch or reflection mechanism.
|
||||
The intent is specifically not to demonstrate heroic measures such as peeking and poking raw memory.
|
||||
|
||||
Note that cheating on your type system is almost universally regarded
|
||||
as unidiomatic at best, and poor programming practice at worst.
|
||||
Nonetheless, if your language intentionally maintains a double-standard for OO privacy, here's where you can show it off.
|
||||
41
Task/Break-OO-privacy/ABAP/break-oo-privacy.abap
Normal file
41
Task/Break-OO-privacy/ABAP/break-oo-privacy.abap
Normal file
|
|
@ -0,0 +1,41 @@
|
|||
class friendly_class definition deferred.
|
||||
|
||||
class my_class definition friends friendly_class .
|
||||
|
||||
public section.
|
||||
methods constructor.
|
||||
|
||||
private section.
|
||||
data secret type char30.
|
||||
|
||||
endclass.
|
||||
|
||||
class my_class implementation .
|
||||
|
||||
method constructor.
|
||||
secret = 'a password'. " Instantiate secret.
|
||||
endmethod.
|
||||
|
||||
endclass.
|
||||
|
||||
class friendly_class definition create public .
|
||||
|
||||
public section.
|
||||
methods return_secret
|
||||
returning value(r_secret) type char30.
|
||||
|
||||
endclass.
|
||||
|
||||
class friendly_class implementation.
|
||||
|
||||
method return_secret.
|
||||
|
||||
data lr_my_class type ref to my_class.
|
||||
|
||||
create object lr_my_class. " Instantiate my_class
|
||||
|
||||
write lr_my_class->secret. " Here's the privacy violation.
|
||||
|
||||
endmethod.
|
||||
|
||||
endclass.
|
||||
10
Task/Break-OO-privacy/Ada/break-oo-privacy-1.ada
Normal file
10
Task/Break-OO-privacy/Ada/break-oo-privacy-1.ada
Normal file
|
|
@ -0,0 +1,10 @@
|
|||
package OO_Privacy is
|
||||
|
||||
type Confidential_Stuff is tagged private;
|
||||
subtype Password_Type is String(1 .. 8);
|
||||
|
||||
private
|
||||
type Confidential_Stuff is tagged record
|
||||
Password: Password_Type := "default!"; -- the "secret"
|
||||
end record;
|
||||
end OO_Privacy;
|
||||
16
Task/Break-OO-privacy/Ada/break-oo-privacy-2.ada
Normal file
16
Task/Break-OO-privacy/Ada/break-oo-privacy-2.ada
Normal file
|
|
@ -0,0 +1,16 @@
|
|||
with OO_Privacy, Ada.Unchecked_Conversion, Ada.Text_IO;
|
||||
|
||||
procedure OO_Break_Privacy is
|
||||
|
||||
type Hacker_Stuff is tagged record
|
||||
Password: OO_Privacy.Password_Type := "?unknown";
|
||||
end record;
|
||||
|
||||
function Hack is new Ada.Unchecked_Conversion
|
||||
(Source => OO_Privacy.Confidential_Stuff, Target => Hacker_Stuff);
|
||||
|
||||
C: OO_Privacy.Confidential_Stuff; -- which password is hidden inside C?
|
||||
|
||||
begin
|
||||
Ada.Text_IO.Put_Line("The secret password is """ & Hack(C).Password & """");
|
||||
end OO_Break_Privacy;
|
||||
5
Task/Break-OO-privacy/Ada/break-oo-privacy-3.ada
Normal file
5
Task/Break-OO-privacy/Ada/break-oo-privacy-3.ada
Normal file
|
|
@ -0,0 +1,5 @@
|
|||
package OO_Privacy.Friend is -- child package of OO.Privacy
|
||||
|
||||
function Get_Password(Secret: Confidential_Stuff) return String;
|
||||
|
||||
end OO_Privacy.Friend;
|
||||
6
Task/Break-OO-privacy/Ada/break-oo-privacy-4.ada
Normal file
6
Task/Break-OO-privacy/Ada/break-oo-privacy-4.ada
Normal file
|
|
@ -0,0 +1,6 @@
|
|||
package body OO_Privacy.Friend is -- implementation of the child package
|
||||
|
||||
function Get_Password(Secret: Confidential_Stuff) return String is
|
||||
(Secret.Password);
|
||||
|
||||
end OO_Privacy.Friend;
|
||||
11
Task/Break-OO-privacy/Ada/break-oo-privacy-5.ada
Normal file
11
Task/Break-OO-privacy/Ada/break-oo-privacy-5.ada
Normal file
|
|
@ -0,0 +1,11 @@
|
|||
with OO_Privacy.Friend, Ada.Text_IO;
|
||||
|
||||
procedure Bypass_OO_Privacy is
|
||||
|
||||
C: OO_Privacy.Confidential_Stuff; -- which password is hidden inside C?
|
||||
|
||||
begin
|
||||
Ada.Text_IO.Put_Line("Password: """ &
|
||||
OO_Privacy.Friend.Get_Password(C) &
|
||||
"""");
|
||||
end Bypass_OO_Privacy;
|
||||
67
Task/Break-OO-privacy/C++/break-oo-privacy-1.cpp
Normal file
67
Task/Break-OO-privacy/C++/break-oo-privacy-1.cpp
Normal file
|
|
@ -0,0 +1,67 @@
|
|||
#include <iostream>
|
||||
|
||||
class CWidget; // Forward-declare that we have a class named CWidget.
|
||||
|
||||
class CFactory
|
||||
{
|
||||
friend class CWidget;
|
||||
private:
|
||||
unsigned int m_uiCount;
|
||||
public:
|
||||
CFactory();
|
||||
~CFactory();
|
||||
CWidget* GetWidget();
|
||||
};
|
||||
|
||||
class CWidget
|
||||
{
|
||||
private:
|
||||
CFactory& m_parent;
|
||||
|
||||
private:
|
||||
CWidget(); // Disallow the default constructor.
|
||||
CWidget(const CWidget&); // Disallow the copy constructor
|
||||
CWidget& operator=(const CWidget&); // Disallow the assignment operator.
|
||||
public:
|
||||
CWidget(CFactory& parent);
|
||||
~CWidget();
|
||||
};
|
||||
|
||||
// CFactory constructors and destructors. Very simple things.
|
||||
CFactory::CFactory() : m_uiCount(0) {}
|
||||
CFactory::~CFactory() {}
|
||||
|
||||
// CFactory method which creates CWidgets.
|
||||
CWidget* CFactory::GetWidget()
|
||||
{
|
||||
// Create a new CWidget, tell it we're its parent.
|
||||
return new CWidget(*this);
|
||||
}
|
||||
|
||||
// CWidget constructor
|
||||
CWidget::CWidget(CFactory& parent) : m_parent(parent)
|
||||
{
|
||||
++m_parent.m_uiCount;
|
||||
|
||||
std::cout << "Widget spawning. There are now " << m_parent.m_uiCount << " Widgets instanciated." << std::endl;
|
||||
}
|
||||
|
||||
CWidget::~CWidget()
|
||||
{
|
||||
--m_parent.m_uiCount;
|
||||
|
||||
std::cout << "Widget dieing. There are now " << m_parent.m_uiCount << " Widgets instanciated." << std::endl;
|
||||
}
|
||||
|
||||
int main()
|
||||
{
|
||||
CFactory factory;
|
||||
|
||||
CWidget* pWidget1 = factory.GetWidget();
|
||||
CWidget* pWidget2 = factory.GetWidget();
|
||||
delete pWidget1;
|
||||
|
||||
CWidget* pWidget3 = factory.GetWidget();
|
||||
delete pWidget3;
|
||||
delete pWidget2;
|
||||
}
|
||||
6
Task/Break-OO-privacy/C++/break-oo-privacy-2.cpp
Normal file
6
Task/Break-OO-privacy/C++/break-oo-privacy-2.cpp
Normal file
|
|
@ -0,0 +1,6 @@
|
|||
Widget spawning. There are now 1 Widgets instanciated.
|
||||
Widget spawning. There are now 2 Widgets instanciated.
|
||||
Widget dieing. There are now 1 Widgets instanciated.
|
||||
Widget spawning. There are now 2 Widgets instanciated.
|
||||
Widget dieing. There are now 1 Widgets instanciated.
|
||||
Widget dieing. There are now 0 Widgets instanciated.
|
||||
66
Task/Break-OO-privacy/C++/break-oo-privacy-3.cpp
Normal file
66
Task/Break-OO-privacy/C++/break-oo-privacy-3.cpp
Normal file
|
|
@ -0,0 +1,66 @@
|
|||
#include <iostream>
|
||||
|
||||
class CWidget; // Forward-declare that we have a class named CWidget.
|
||||
|
||||
class CFactory
|
||||
{
|
||||
private:
|
||||
unsigned int m_uiCount;
|
||||
public:
|
||||
CFactory();
|
||||
~CFactory();
|
||||
CWidget* GetWidget();
|
||||
};
|
||||
|
||||
class CWidget
|
||||
{
|
||||
private:
|
||||
unsigned int* m_pCounter;
|
||||
|
||||
private:
|
||||
CWidget(); // Disallow the default constructor.
|
||||
CWidget(const CWidget&); // Disallow the copy constructor
|
||||
CWidget& operator=(const CWidget&); // Disallow the assignment operator.
|
||||
public:
|
||||
CWidget(unsigned int* pCounter);
|
||||
~CWidget();
|
||||
};
|
||||
|
||||
// CFactory constructors and destructors. Very simple things.
|
||||
CFactory::CFactory() : m_uiCount(0) {}
|
||||
CFactory::~CFactory() {}
|
||||
|
||||
// CFactory method which creates CWidgets.
|
||||
CWidget* CFactory::GetWidget()
|
||||
{
|
||||
// Create a new CWidget, tell it we're its parent.
|
||||
return new CWidget(&m_uiCount);
|
||||
}
|
||||
|
||||
// CWidget constructor
|
||||
CWidget::CWidget(unsigned int* pCounter) : m_pCounter(pCounter)
|
||||
{
|
||||
++*m_pCounter;
|
||||
|
||||
std::cout << "Widget spawning. There are now " << *m_pCounter<< " Widgets instanciated." << std::endl;
|
||||
}
|
||||
|
||||
CWidget::~CWidget()
|
||||
{
|
||||
--*m_pCounter;
|
||||
|
||||
std::cout << "Widget dieing. There are now " << *m_pCounter<< " Widgets instanciated." << std::endl;
|
||||
}
|
||||
|
||||
int main()
|
||||
{
|
||||
CFactory factory;
|
||||
|
||||
CWidget* pWidget1 = factory.GetWidget();
|
||||
CWidget* pWidget2 = factory.GetWidget();
|
||||
delete pWidget1;
|
||||
|
||||
CWidget* pWidget3 = factory.GetWidget();
|
||||
delete pWidget3;
|
||||
delete pWidget2;
|
||||
}
|
||||
18
Task/Break-OO-privacy/C-sharp/break-oo-privacy-1.cs
Normal file
18
Task/Break-OO-privacy/C-sharp/break-oo-privacy-1.cs
Normal file
|
|
@ -0,0 +1,18 @@
|
|||
using System;
|
||||
using System.Reflection;
|
||||
|
||||
public class MyClass
|
||||
{
|
||||
private int answer = 42;
|
||||
}
|
||||
|
||||
public class Program
|
||||
{
|
||||
public static void Main()
|
||||
{
|
||||
var myInstance = new MyClass();
|
||||
var fieldInfo = typeof(MyClass).GetField("answer", BindingFlags.NonPublic | BindingFlags.Instance);
|
||||
var answer = fieldInfo.GetValue(myInstance);
|
||||
Console.WriteLine(answer);
|
||||
}
|
||||
}
|
||||
1
Task/Break-OO-privacy/C-sharp/break-oo-privacy-2.cs
Normal file
1
Task/Break-OO-privacy/C-sharp/break-oo-privacy-2.cs
Normal file
|
|
@ -0,0 +1 @@
|
|||
42
|
||||
7
Task/Break-OO-privacy/Clojure/break-oo-privacy-1.clj
Normal file
7
Task/Break-OO-privacy/Clojure/break-oo-privacy-1.clj
Normal file
|
|
@ -0,0 +1,7 @@
|
|||
(ns a)
|
||||
(def ^:private priv :secret)
|
||||
|
||||
; From REPL, in another namespace 'user':
|
||||
user=> @a/priv ; fails with: IllegalStateException: var: a/priv is not public
|
||||
user=> @#'a/priv ; succeeds
|
||||
:secret
|
||||
2
Task/Break-OO-privacy/Clojure/break-oo-privacy-2.clj
Normal file
2
Task/Break-OO-privacy/Clojure/break-oo-privacy-2.clj
Normal file
|
|
@ -0,0 +1,2 @@
|
|||
user=> (get-field Double "serialVersionUID" (Double/valueOf 1.0))
|
||||
-9172774392245257468
|
||||
44
Task/Break-OO-privacy/Common-Lisp/break-oo-privacy.lisp
Normal file
44
Task/Break-OO-privacy/Common-Lisp/break-oo-privacy.lisp
Normal file
|
|
@ -0,0 +1,44 @@
|
|||
(defpackage :funky
|
||||
;; only these symbols are public
|
||||
(:export :widget :get-wobbliness)
|
||||
;; for convenience, bring common lisp symbols into funky
|
||||
(:use :cl))
|
||||
|
||||
;; switch reader to funky package: all symbols that are
|
||||
;; not from the CL package are interned in FUNKY.
|
||||
|
||||
(in-package :funky)
|
||||
|
||||
(defclass widget ()
|
||||
;; :initarg -> slot "wobbliness" is initialized using :wobbliness keyword
|
||||
;; :initform -> if initarg is missing, slot defaults to 42
|
||||
;; :reader -> a "getter" method called get-wobbliness is generated
|
||||
((wobbliness :initarg :wobbliness :initform 42 :reader get-wobbliness)))
|
||||
|
||||
;; simulate being in another source file with its own package:
|
||||
;; cool package gets external symbols from funky, and cl:
|
||||
(defpackage :cool
|
||||
(:use :funky :cl))
|
||||
|
||||
(in-package :cool)
|
||||
|
||||
;; we can use the symbol funky:widget without any package prefix:
|
||||
(defvar *w* (make-instance 'widget :wobbliness 36))
|
||||
|
||||
;; ditto with funky:get-wobbliness
|
||||
(format t "wobbliness: ~a~%" (get-wobbliness *w*))
|
||||
|
||||
;; direct access to the slot requires fully qualified private symbol
|
||||
;; and double colon:
|
||||
(format t "wobbliness: ~a~%" (slot-value *w* 'funky::wobbliness))
|
||||
|
||||
;; if we use unqualified wobbliness, it's a different symbol:
|
||||
;; it is cool::wobbliness interned in our local package.
|
||||
;; we do not have funky:wobbliness because it's not exported by funky.
|
||||
(unless (ignore-errors
|
||||
(format t "wobbliness: ~a~%" (slot-value *w* 'wobbliness)))
|
||||
(write-line "didn't work"))
|
||||
|
||||
;; single colon results in error at read time! The expression is not
|
||||
;; even read and evaluated. The symbol is internal and so cannot be used.
|
||||
(format t "wobbliness: ~a~%" (slot-value *w* 'funky:wobbliness))
|
||||
11
Task/Break-OO-privacy/D/break-oo-privacy-1.d
Normal file
11
Task/Break-OO-privacy/D/break-oo-privacy-1.d
Normal file
|
|
@ -0,0 +1,11 @@
|
|||
module breakingprivacy;
|
||||
|
||||
struct Foo
|
||||
{
|
||||
int[] arr;
|
||||
|
||||
private:
|
||||
int x;
|
||||
string str;
|
||||
float f;
|
||||
}
|
||||
16
Task/Break-OO-privacy/D/break-oo-privacy-2.d
Normal file
16
Task/Break-OO-privacy/D/break-oo-privacy-2.d
Normal file
|
|
@ -0,0 +1,16 @@
|
|||
import std.stdio;
|
||||
import breakingprivacy;
|
||||
|
||||
void main()
|
||||
{
|
||||
auto foo = Foo([1,2,3], 42, "Hello World!", 3.14);
|
||||
writeln(foo);
|
||||
|
||||
// __traits(getMember, obj, name) allows you to access any field of obj given its name
|
||||
// Reading a private field
|
||||
writeln("foo.x = ", __traits(getMember, foo, "x"));
|
||||
|
||||
// Writing to a private field
|
||||
__traits(getMember, foo, "str") = "Not so private anymore!";
|
||||
writeln("Modified foo: ", foo);
|
||||
}
|
||||
3
Task/Break-OO-privacy/D/break-oo-privacy-3.d
Normal file
3
Task/Break-OO-privacy/D/break-oo-privacy-3.d
Normal file
|
|
@ -0,0 +1,3 @@
|
|||
Foo([1, 2, 3], 42, "Hello World!", 3.14)
|
||||
foo.x = 42
|
||||
Modified foo: Foo([1, 2, 3], 42, "Not so private anymore!", 3.14)
|
||||
45
Task/Break-OO-privacy/Ecstasy/break-oo-privacy.ecstasy
Normal file
45
Task/Break-OO-privacy/Ecstasy/break-oo-privacy.ecstasy
Normal file
|
|
@ -0,0 +1,45 @@
|
|||
module BreakOO {
|
||||
/**
|
||||
* This is a class with public, protected, and private properties.
|
||||
*/
|
||||
class Exposed {
|
||||
public String pub = "public";
|
||||
protected String pro = "protected";
|
||||
private String pri = "private";
|
||||
|
||||
@Override
|
||||
String toString() {
|
||||
return $"pub={pub.quoted()}, pro={pro.quoted()}, pri={pri.quoted()}";
|
||||
}
|
||||
}
|
||||
|
||||
void run() {
|
||||
@Inject Console console;
|
||||
|
||||
Exposed expo = new Exposed();
|
||||
console.print($"before: {expo}");
|
||||
|
||||
// you can only access public members from the default reference
|
||||
expo.pub = $"this was {expo.pub}";
|
||||
// expo.pro = $"this was {expo.pro}"; <- compiler error
|
||||
// expo.pri = $"this was {expo.pri}"; <- compiler error
|
||||
|
||||
// but you can ask for the protected reference ...
|
||||
assert (protected Exposed) expoPro := &expo.revealAs((protected Exposed));
|
||||
expoPro.pro = $"this was {expoPro.pro}";
|
||||
// expoPro.pri = $"this was {expoPro.pri}"; <- compiler error
|
||||
|
||||
// and you can ask for the private reference ...
|
||||
assert (private Exposed) expoPri := &expo.revealAs((private Exposed));
|
||||
expoPri.pri = $"this was {expoPri.pri}";
|
||||
|
||||
// or you can ask for the underlying struct, which is a passive
|
||||
// object that contains only the field storage
|
||||
assert (struct Exposed) expoStr := &expo.revealAs((struct Exposed));
|
||||
expoStr.pub = $"{expoStr.pub}!!!";
|
||||
expoStr.pro = $"{expoStr.pro}!!!";
|
||||
expoStr.pri = $"{expoStr.pri}!!!";
|
||||
|
||||
console.print($"after: {expo}");
|
||||
}
|
||||
}
|
||||
16
Task/Break-OO-privacy/F-Sharp/break-oo-privacy.fs
Normal file
16
Task/Break-OO-privacy/F-Sharp/break-oo-privacy.fs
Normal file
|
|
@ -0,0 +1,16 @@
|
|||
open System
|
||||
open System.Reflection
|
||||
|
||||
type MyClass() =
|
||||
let answer = 42
|
||||
member this.GetAnswer
|
||||
with get() = answer
|
||||
|
||||
|
||||
[<EntryPoint>]
|
||||
let main argv =
|
||||
let myInstance = MyClass()
|
||||
let fieldInfo = myInstance.GetType().GetField("answer", BindingFlags.NonPublic ||| BindingFlags.Instance)
|
||||
let answer = fieldInfo.GetValue(myInstance)
|
||||
printfn "%s = %A" (answer.GetType().ToString()) answer
|
||||
0
|
||||
3
Task/Break-OO-privacy/Factor/break-oo-privacy-1.factor
Normal file
3
Task/Break-OO-privacy/Factor/break-oo-privacy-1.factor
Normal file
|
|
@ -0,0 +1,3 @@
|
|||
( scratchpad ) USING: sets sets.private ;
|
||||
( scratchpad ) { 1 2 3 } { 1 2 4 } sequence/tester count .
|
||||
2
|
||||
3
Task/Break-OO-privacy/Factor/break-oo-privacy-2.factor
Normal file
3
Task/Break-OO-privacy/Factor/break-oo-privacy-2.factor
Normal file
|
|
@ -0,0 +1,3 @@
|
|||
( scratchpad ) USE: sets
|
||||
( scratchpad ) { 1 2 3 } { 1 2 4 } intersect length .
|
||||
2
|
||||
17
Task/Break-OO-privacy/Forth/break-oo-privacy.fth
Normal file
17
Task/Break-OO-privacy/Forth/break-oo-privacy.fth
Normal file
|
|
@ -0,0 +1,17 @@
|
|||
include FMS-SI.f
|
||||
|
||||
99 value x \ create a global variable named x
|
||||
|
||||
:class foo
|
||||
ivar x \ this x is private to the class foo
|
||||
:m init: 10 x ! ;m \ constructor
|
||||
:m print x ? ;m
|
||||
;class
|
||||
|
||||
foo f1 \ instantiate a foo object
|
||||
f1 print \ 10 access the private x with the print message
|
||||
|
||||
x . \ 99 x is a globally scoped name
|
||||
|
||||
50 .. f1.x ! \ use the dot parser to access the private x without a message
|
||||
f1 print \ 50
|
||||
21
Task/Break-OO-privacy/FreeBASIC/break-oo-privacy.basic
Normal file
21
Task/Break-OO-privacy/FreeBASIC/break-oo-privacy.basic
Normal file
|
|
@ -0,0 +1,21 @@
|
|||
'FB 1.05.0 Win64
|
||||
|
||||
#Undef Private
|
||||
#Undef Protected
|
||||
#Define Private Public
|
||||
#Define Protected Public
|
||||
|
||||
Type MyType
|
||||
Public :
|
||||
x As Integer = 1
|
||||
Protected :
|
||||
y As Integer = 2
|
||||
Private :
|
||||
z As Integer = 3
|
||||
End Type
|
||||
|
||||
Dim mt As MyType
|
||||
Print mt.x, mt.y, mt.z
|
||||
Print
|
||||
Print "Press any key to quit"
|
||||
Sleep
|
||||
88
Task/Break-OO-privacy/Go/break-oo-privacy-1.go
Normal file
88
Task/Break-OO-privacy/Go/break-oo-privacy-1.go
Normal file
|
|
@ -0,0 +1,88 @@
|
|||
package main
|
||||
|
||||
import (
|
||||
"bufio"
|
||||
"errors"
|
||||
"fmt"
|
||||
"os"
|
||||
"reflect"
|
||||
"unsafe"
|
||||
)
|
||||
|
||||
type foobar struct {
|
||||
Exported int // In Go identifiers that are capitalized are exported,
|
||||
unexported int // while lowercase identifiers are not.
|
||||
}
|
||||
|
||||
func main() {
|
||||
obj := foobar{12, 42}
|
||||
fmt.Println("obj:", obj)
|
||||
|
||||
examineAndModify(&obj)
|
||||
fmt.Println("obj:", obj)
|
||||
|
||||
anotherExample()
|
||||
}
|
||||
|
||||
// For simplicity this skips several checks. It assumes the thing in the
|
||||
// interface is a pointer without checking (v.Kind()==reflect.Ptr),
|
||||
// it then assumes it is a structure type with two int fields
|
||||
// (v.Kind()==reflect.Struct, f.Type()==reflect.TypeOf(int(0))).
|
||||
func examineAndModify(any interface{}) {
|
||||
v := reflect.ValueOf(any) // get a reflect.Value
|
||||
v = v.Elem() // dereference the pointer
|
||||
fmt.Println(" v:", v, "=", v.Interface())
|
||||
t := v.Type()
|
||||
// Loop through the struct fields
|
||||
fmt.Printf(" %3s %-10s %-4s %s\n", "Idx", "Name", "Type", "CanSet")
|
||||
for i := 0; i < v.NumField(); i++ {
|
||||
f := v.Field(i) // reflect.Value of the field
|
||||
fmt.Printf(" %2d: %-10s %-4s %t\n", i,
|
||||
t.Field(i).Name, f.Type(), f.CanSet())
|
||||
}
|
||||
|
||||
// "Exported", field 0, has CanSet==true so we can do:
|
||||
v.Field(0).SetInt(16)
|
||||
// "unexported", field 1, has CanSet==false so the following
|
||||
// would fail at run-time with:
|
||||
// panic: reflect: reflect.Value.SetInt using value obtained using unexported field
|
||||
//v.Field(1).SetInt(43)
|
||||
|
||||
// However, we can bypass this restriction with the unsafe
|
||||
// package once we know what type it is (so we can use the
|
||||
// correct pointer type, here *int):
|
||||
vp := v.Field(1).Addr() // Take the fields's address
|
||||
up := unsafe.Pointer(vp.Pointer()) // … get an int value of the address and convert it "unsafely"
|
||||
p := (*int)(up) // … and end up with what we want/need
|
||||
fmt.Printf(" vp has type %-14T = %v\n", vp, vp)
|
||||
fmt.Printf(" up has type %-14T = %#0x\n", up, up)
|
||||
fmt.Printf(" p has type %-14T = %v pointing at %v\n", p, p, *p)
|
||||
*p = 43 // effectively obj.unexported = 43
|
||||
// or an incr all on one ulgy line:
|
||||
*(*int)(unsafe.Pointer(v.Field(1).Addr().Pointer()))++
|
||||
|
||||
// Note that as-per the package "unsafe" documentation,
|
||||
// the return value from vp.Pointer *must* be converted to
|
||||
// unsafe.Pointer in the same expression; the result is fragile.
|
||||
//
|
||||
// I.e. it is invalid to do:
|
||||
// thisIsFragile := vp.Pointer()
|
||||
// up := unsafe.Pointer(thisIsFragile)
|
||||
}
|
||||
|
||||
// This time we'll use an external package to demonstrate that it's not
|
||||
// restricted to things defined locally. We'll mess with bufio.Reader's
|
||||
// interal workings by happening to know they have a non-exported
|
||||
// "err error" field. Of course future versions of Go may not have this
|
||||
// field or use it in the same way :).
|
||||
func anotherExample() {
|
||||
r := bufio.NewReader(os.Stdin)
|
||||
|
||||
// Do the dirty stuff in one ugly and unsafe statement:
|
||||
errp := (*error)(unsafe.Pointer(
|
||||
reflect.ValueOf(r).Elem().FieldByName("err").Addr().Pointer()))
|
||||
*errp = errors.New("unsafely injected error value into bufio inner workings")
|
||||
|
||||
_, err := r.ReadByte()
|
||||
fmt.Println("bufio.ReadByte returned error:", err)
|
||||
}
|
||||
17
Task/Break-OO-privacy/Go/break-oo-privacy-2.go
Normal file
17
Task/Break-OO-privacy/Go/break-oo-privacy-2.go
Normal file
|
|
@ -0,0 +1,17 @@
|
|||
link printf
|
||||
|
||||
procedure main()
|
||||
(x := foo(1,2,3)).print() # create and show a foo
|
||||
printf("Fieldnames of foo x : ") # show fieldnames
|
||||
every printf(" %i",fieldnames(x)) # __s (self), __m (methods), vars
|
||||
printf("\n")
|
||||
printf("var 1 of foo x = %i\n", x.var1) # read var1 from outside x
|
||||
x.var1 := -1 # change var1 from outside x
|
||||
x.print() # show we changed it
|
||||
end
|
||||
|
||||
class foo(var1,var2,var3) # class with no set/read methods
|
||||
method print()
|
||||
printf("foo var1=%i, var2=%i, var3=%i\n",var1,var2,var3)
|
||||
end
|
||||
end
|
||||
4
Task/Break-OO-privacy/Java/break-oo-privacy-1.java
Normal file
4
Task/Break-OO-privacy/Java/break-oo-privacy-1.java
Normal file
|
|
@ -0,0 +1,4 @@
|
|||
class Example {
|
||||
String stringA = "rosetta";
|
||||
private String stringB = "code";
|
||||
}
|
||||
2
Task/Break-OO-privacy/Java/break-oo-privacy-2.java
Normal file
2
Task/Break-OO-privacy/Java/break-oo-privacy-2.java
Normal file
|
|
@ -0,0 +1,2 @@
|
|||
Example example = new Example();
|
||||
Field field = example.getClass().getDeclaredField("stringB");
|
||||
1
Task/Break-OO-privacy/Java/break-oo-privacy-3.java
Normal file
1
Task/Break-OO-privacy/Java/break-oo-privacy-3.java
Normal file
|
|
@ -0,0 +1 @@
|
|||
field.setAccessible(true);
|
||||
1
Task/Break-OO-privacy/Java/break-oo-privacy-4.java
Normal file
1
Task/Break-OO-privacy/Java/break-oo-privacy-4.java
Normal file
|
|
@ -0,0 +1 @@
|
|||
String stringB = (String) field.get(example);
|
||||
6
Task/Break-OO-privacy/Java/break-oo-privacy-5.java
Normal file
6
Task/Break-OO-privacy/Java/break-oo-privacy-5.java
Normal file
|
|
@ -0,0 +1,6 @@
|
|||
Example example = new Example();
|
||||
Field field = example.getClass().getDeclaredField("stringB");
|
||||
field.setAccessible(true);
|
||||
String stringA = example.stringA;
|
||||
String stringB = (String) field.get(example);
|
||||
System.out.println(stringA + " " + stringB);
|
||||
7
Task/Break-OO-privacy/Java/break-oo-privacy-6.java
Normal file
7
Task/Break-OO-privacy/Java/break-oo-privacy-6.java
Normal file
|
|
@ -0,0 +1,7 @@
|
|||
class Example {
|
||||
String stringA = "rosetta";
|
||||
|
||||
private String stringB() {
|
||||
return "code";
|
||||
}
|
||||
}
|
||||
6
Task/Break-OO-privacy/Java/break-oo-privacy-7.java
Normal file
6
Task/Break-OO-privacy/Java/break-oo-privacy-7.java
Normal file
|
|
@ -0,0 +1,6 @@
|
|||
Example example = new Example();
|
||||
Method method = example.getClass().getDeclaredMethod("stringB");
|
||||
method.setAccessible(true);
|
||||
String stringA = example.stringA;
|
||||
String stringB = (String) method.invoke(example);
|
||||
System.out.println(stringA + " " + stringB);
|
||||
16
Task/Break-OO-privacy/Kotlin/break-oo-privacy.kotlin
Normal file
16
Task/Break-OO-privacy/Kotlin/break-oo-privacy.kotlin
Normal file
|
|
@ -0,0 +1,16 @@
|
|||
import kotlin.reflect.full.declaredMemberProperties
|
||||
import kotlin.reflect.jvm.isAccessible
|
||||
|
||||
class ToBeBroken {
|
||||
@Suppress("unused")
|
||||
private val secret: Int = 42
|
||||
}
|
||||
|
||||
fun main(args: Array<String>) {
|
||||
val tbb = ToBeBroken()
|
||||
val props = ToBeBroken::class.declaredMemberProperties
|
||||
for (prop in props) {
|
||||
prop.isAccessible = true // make private properties accessible
|
||||
println("${prop.name} -> ${prop.get(tbb)}")
|
||||
}
|
||||
}
|
||||
12
Task/Break-OO-privacy/Logtalk/break-oo-privacy-1.logtalk
Normal file
12
Task/Break-OO-privacy/Logtalk/break-oo-privacy-1.logtalk
Normal file
|
|
@ -0,0 +1,12 @@
|
|||
:- object(foo).
|
||||
|
||||
% be sure that context switching calls are allowed
|
||||
:- set_logtalk_flag(context_switching_calls, allow).
|
||||
|
||||
% declare and define a private method
|
||||
:- private(bar/1).
|
||||
bar(1).
|
||||
bar(2).
|
||||
bar(3).
|
||||
|
||||
:- end_object.
|
||||
5
Task/Break-OO-privacy/Logtalk/break-oo-privacy-2.logtalk
Normal file
5
Task/Break-OO-privacy/Logtalk/break-oo-privacy-2.logtalk
Normal file
|
|
@ -0,0 +1,5 @@
|
|||
| ?- foo<<bar(X).
|
||||
X = 1 ;
|
||||
X = 2 ;
|
||||
X = 3
|
||||
true
|
||||
30
Task/Break-OO-privacy/Lua/break-oo-privacy.lua
Normal file
30
Task/Break-OO-privacy/Lua/break-oo-privacy.lua
Normal file
|
|
@ -0,0 +1,30 @@
|
|||
local function Counter()
|
||||
-- These two variables are "private" to this function and can normally
|
||||
-- only be accessed from within this scope, including by any function
|
||||
-- created inside here.
|
||||
local counter = {}
|
||||
local count = 0
|
||||
|
||||
function counter:increment()
|
||||
-- 'count' is an upvalue here and can thus be accessed through the
|
||||
-- debug library, as long as we have a reference to this function.
|
||||
count = count + 1
|
||||
end
|
||||
|
||||
return counter
|
||||
end
|
||||
|
||||
-- Create a counter object and try to access the local 'count' variable.
|
||||
local counter = Counter()
|
||||
|
||||
for i = 1, math.huge do
|
||||
local name, value = debug.getupvalue(counter.increment, i)
|
||||
if not name then break end -- No more upvalues.
|
||||
|
||||
if name == "count" then
|
||||
print("Found 'count', which is "..tostring(value))
|
||||
-- If the 'counter.increment' function didn't access 'count'
|
||||
-- directly then we would never get here.
|
||||
break
|
||||
end
|
||||
end
|
||||
|
|
@ -0,0 +1,20 @@
|
|||
Module CheckIt {
|
||||
Group Alfa {
|
||||
Private:
|
||||
X=10, Y=20
|
||||
Public:
|
||||
Module SetXY (.X, .Y) {}
|
||||
Module Print {
|
||||
Print .X, .Y
|
||||
}
|
||||
}
|
||||
Alfa.Print ' 10 20
|
||||
\\ we have to KnΟw position in group
|
||||
\\ so we make references from two first
|
||||
Read From Alfa, K, M
|
||||
Print K=10, M=20
|
||||
K+=10
|
||||
M+=1000
|
||||
Alfa.Print ' 20 1020
|
||||
}
|
||||
CheckIt
|
||||
7
Task/Break-OO-privacy/Nim/break-oo-privacy-1.nim
Normal file
7
Task/Break-OO-privacy/Nim/break-oo-privacy-1.nim
Normal file
|
|
@ -0,0 +1,7 @@
|
|||
type Foo* = object
|
||||
a: string
|
||||
b: string
|
||||
c: int
|
||||
|
||||
proc createFoo*(a, b, c): Foo =
|
||||
Foo(a: a, b: b, c: c)
|
||||
3
Task/Break-OO-privacy/Nim/break-oo-privacy-2.nim
Normal file
3
Task/Break-OO-privacy/Nim/break-oo-privacy-2.nim
Normal file
|
|
@ -0,0 +1,3 @@
|
|||
var x = createFoo("this a", "this b", 12)
|
||||
|
||||
echo x.a # compile time error
|
||||
1
Task/Break-OO-privacy/Nim/break-oo-privacy-3.nim
Normal file
1
Task/Break-OO-privacy/Nim/break-oo-privacy-3.nim
Normal file
|
|
@ -0,0 +1 @@
|
|||
echo repr(x)
|
||||
11
Task/Break-OO-privacy/Nim/break-oo-privacy-4.nim
Normal file
11
Task/Break-OO-privacy/Nim/break-oo-privacy-4.nim
Normal file
|
|
@ -0,0 +1,11 @@
|
|||
import typeinfo
|
||||
|
||||
for key, val in fields(toAny(x)):
|
||||
echo "Key ", key
|
||||
case val.kind
|
||||
of akString:
|
||||
echo " is a string with value: ", val.getString
|
||||
of akInt..akInt64, akUint..akUint64:
|
||||
echo " is an integer with value: ", val.getBiggestInt
|
||||
else:
|
||||
echo " is an unknown with value: ", val.repr
|
||||
33
Task/Break-OO-privacy/OCaml/break-oo-privacy.ocaml
Normal file
33
Task/Break-OO-privacy/OCaml/break-oo-privacy.ocaml
Normal file
|
|
@ -0,0 +1,33 @@
|
|||
class point x y =
|
||||
object
|
||||
val mutable x = x
|
||||
val mutable y = y
|
||||
method print = Printf.printf "(%d, %d)\n" x y
|
||||
method dance =
|
||||
x <- x + Random.int 3 - 1;
|
||||
y <- y + Random.int 3 - 1
|
||||
end
|
||||
|
||||
type evil_point {
|
||||
blah : int;
|
||||
blah2 : int;
|
||||
mutable x : int;
|
||||
mutable y : int;
|
||||
}
|
||||
|
||||
let evil_reset p =
|
||||
let ep = Obj.magic p in
|
||||
ep.x <- 0;
|
||||
ep.y <- 0
|
||||
|
||||
let () =
|
||||
let p = new point 0 0 in
|
||||
p#print;
|
||||
p#dance;
|
||||
p#print;
|
||||
p#dance;
|
||||
p#print;
|
||||
let (_, _, x, y) : int * int * int * int = Obj.magic p in
|
||||
Printf.printf "Broken coord: (%d, %d)\n" x y;
|
||||
evil_reset p
|
||||
p#print
|
||||
36
Task/Break-OO-privacy/Objective-C/break-oo-privacy-1.m
Normal file
36
Task/Break-OO-privacy/Objective-C/break-oo-privacy-1.m
Normal file
|
|
@ -0,0 +1,36 @@
|
|||
#import <Foundation/Foundation.h>
|
||||
|
||||
@interface Example : NSObject {
|
||||
@private
|
||||
NSString *_name;
|
||||
}
|
||||
- (instancetype)initWithName:(NSString *)name;
|
||||
@end
|
||||
|
||||
@implementation Example
|
||||
- (NSString *)description {
|
||||
return [NSString stringWithFormat:@"Hello, I am %@", _name];
|
||||
}
|
||||
- (instancetype)initWithName:(NSString *)name {
|
||||
if ((self = [super init])) {
|
||||
_name = [name copy];
|
||||
}
|
||||
return self;
|
||||
}
|
||||
@end
|
||||
|
||||
int main (int argc, const char * argv[]) {
|
||||
@autoreleasepool{
|
||||
|
||||
Example *foo = [[Example alloc] initWithName:@"Eric"];
|
||||
|
||||
// get private field
|
||||
NSLog(@"%@", [foo valueForKey:@"name"]);
|
||||
|
||||
// set private field
|
||||
[foo setValue:@"Edith" forKey:@"name"];
|
||||
NSLog(@"%@", foo);
|
||||
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
50
Task/Break-OO-privacy/Objective-C/break-oo-privacy-2.m
Normal file
50
Task/Break-OO-privacy/Objective-C/break-oo-privacy-2.m
Normal file
|
|
@ -0,0 +1,50 @@
|
|||
#import <Foundation/Foundation.h>
|
||||
|
||||
@interface Example : NSObject {
|
||||
@private
|
||||
NSString *_name;
|
||||
}
|
||||
- (instancetype)initWithName:(NSString *)name;
|
||||
@end
|
||||
|
||||
@implementation Example
|
||||
- (NSString *)description {
|
||||
return [NSString stringWithFormat:@"Hello, I am %@", _name];
|
||||
}
|
||||
- (instancetype)initWithName:(NSString *)name {
|
||||
if ((self = [super init])) {
|
||||
_name = [name copy];
|
||||
}
|
||||
return self;
|
||||
}
|
||||
@end
|
||||
|
||||
@interface Example (HackName)
|
||||
- (NSString *)getName;
|
||||
- (void)setNameTo:(NSString *)newName;
|
||||
@end
|
||||
|
||||
@implementation Example (HackName)
|
||||
- (NSString *)getName {
|
||||
return _name;
|
||||
}
|
||||
- (void)setNameTo:(NSString *)newName {
|
||||
_name = [newName copy];
|
||||
}
|
||||
@end
|
||||
|
||||
int main (int argc, const char * argv[]) {
|
||||
@autoreleasepool{
|
||||
|
||||
Example *foo = [[Example alloc] initWithName:@"Eric"];
|
||||
|
||||
// get private field
|
||||
NSLog(@"%@", [foo getName]);
|
||||
|
||||
// set private field
|
||||
[foo setNameTo:@"Edith"];
|
||||
NSLog(@"%@", foo);
|
||||
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
38
Task/Break-OO-privacy/Objective-C/break-oo-privacy-3.m
Normal file
38
Task/Break-OO-privacy/Objective-C/break-oo-privacy-3.m
Normal file
|
|
@ -0,0 +1,38 @@
|
|||
#import <Foundation/Foundation.h>
|
||||
#import <objc/runtime.h>
|
||||
|
||||
@interface Example : NSObject {
|
||||
@private
|
||||
NSString *_name;
|
||||
}
|
||||
- (instancetype)initWithName:(NSString *)name;
|
||||
@end
|
||||
|
||||
@implementation Example
|
||||
- (NSString *)description {
|
||||
return [NSString stringWithFormat:@"Hello, I am %@", _name];
|
||||
}
|
||||
- (instancetype)initWithName:(NSString *)name {
|
||||
if ((self = [super init])) {
|
||||
_name = [name copy];
|
||||
}
|
||||
return self;
|
||||
}
|
||||
@end
|
||||
|
||||
int main (int argc, const char * argv[]) {
|
||||
@autoreleasepool{
|
||||
|
||||
Example *foo = [[Example alloc] initWithName:@"Eric"];
|
||||
|
||||
// get private field
|
||||
Ivar nameField = class_getInstanceVariable([foo class], "_name");
|
||||
NSLog(@"%@", object_getIvar(foo, nameField));
|
||||
|
||||
// set private field
|
||||
object_setIvar(foo, nameField, @"Edith");
|
||||
NSLog(@"%@", foo);
|
||||
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
19
Task/Break-OO-privacy/PHP/break-oo-privacy-1.php
Normal file
19
Task/Break-OO-privacy/PHP/break-oo-privacy-1.php
Normal file
|
|
@ -0,0 +1,19 @@
|
|||
<?php
|
||||
class SimpleClass {
|
||||
private $answer = "hello\"world\nforever :)";
|
||||
}
|
||||
|
||||
$class = new SimpleClass;
|
||||
ob_start();
|
||||
|
||||
// var_export() expects class to contain __set_state() method which would import
|
||||
// data from array. But let's ignore this and remove from result the method which
|
||||
// sets state and just leave data which can be used everywhere...
|
||||
var_export($class);
|
||||
$class_content = ob_get_clean();
|
||||
|
||||
$class_content = preg_replace('"^SimpleClass::__set_state\("', 'return ', $class_content);
|
||||
$class_content = preg_replace('"\)$"', ';', $class_content);
|
||||
|
||||
$new_class = eval($class_content);
|
||||
echo $new_class['answer'];
|
||||
8
Task/Break-OO-privacy/PHP/break-oo-privacy-2.php
Normal file
8
Task/Break-OO-privacy/PHP/break-oo-privacy-2.php
Normal file
|
|
@ -0,0 +1,8 @@
|
|||
<?php
|
||||
class SimpleClass {
|
||||
private $answer = 42;
|
||||
}
|
||||
|
||||
$class = new SimpleClass;
|
||||
$classvars = (array)$class;
|
||||
echo $classvars["\0SimpleClass\0answer"];
|
||||
12
Task/Break-OO-privacy/PHP/break-oo-privacy-3.php
Normal file
12
Task/Break-OO-privacy/PHP/break-oo-privacy-3.php
Normal file
|
|
@ -0,0 +1,12 @@
|
|||
<?php
|
||||
class fragile {
|
||||
private $foo = 'bar';
|
||||
}
|
||||
$fragile = new fragile;
|
||||
$ro = new ReflectionObject($fragile);
|
||||
$rp = $ro->getProperty('foo');
|
||||
$rp->setAccessible(true);
|
||||
var_dump($rp->getValue($fragile));
|
||||
$rp->setValue($fragile, 'haxxorz!');
|
||||
var_dump($rp->getValue($fragile));
|
||||
var_dump($fragile);
|
||||
15
Task/Break-OO-privacy/Perl/break-oo-privacy.pl
Normal file
15
Task/Break-OO-privacy/Perl/break-oo-privacy.pl
Normal file
|
|
@ -0,0 +1,15 @@
|
|||
package Foo;
|
||||
sub new {
|
||||
my $class = shift;
|
||||
my $self = { _bar => 'I am ostensibly private' };
|
||||
return bless $self, $class;
|
||||
}
|
||||
|
||||
sub get_bar {
|
||||
my $self = shift;
|
||||
return $self->{_bar};
|
||||
}
|
||||
|
||||
package main;
|
||||
my $foo = Foo->new();
|
||||
print "$_\n" for $foo->get_bar(), $foo->{_bar};
|
||||
18
Task/Break-OO-privacy/Phix/break-oo-privacy.phix
Normal file
18
Task/Break-OO-privacy/Phix/break-oo-privacy.phix
Normal file
|
|
@ -0,0 +1,18 @@
|
|||
(notonline)-->
|
||||
<span style="color: #008080;">without</span> <span style="color: #008080;">js</span> <span style="color: #000080;font-style:italic;">-- (no class under p2js)</span>
|
||||
<span style="color: #008080;">class</span> <span style="color: #000000;">test</span>
|
||||
<span style="color: #008080;">private</span> <span style="color: #004080;">string</span> <span style="color: #000000;">msg</span> <span style="color: #0000FF;">=</span> <span style="color: #008000;">"this is a test"</span>
|
||||
<span style="color: #008080;">procedure</span> <span style="color: #000000;">show</span><span style="color: #0000FF;">()</span> <span style="color: #0000FF;">?</span><span style="color: #7060A8;">this</span><span style="color: #0000FF;">.</span><span style="color: #000000;">msg</span> <span style="color: #008080;">end</span> <span style="color: #008080;">procedure</span>
|
||||
<span style="color: #008080;">end</span> <span style="color: #008080;">class</span>
|
||||
<span style="color: #000000;">test</span> <span style="color: #000000;">t</span> <span style="color: #0000FF;">=</span> <span style="color: #7060A8;">new</span><span style="color: #0000FF;">()</span>
|
||||
<span style="color: #000000;">t</span><span style="color: #0000FF;">.</span><span style="color: #000000;">show</span><span style="color: #0000FF;">()</span>
|
||||
<span style="color: #000080;font-style:italic;">--?t.msg -- illegal
|
||||
--t.msg = "this is broken" -- illegal</span>
|
||||
<span style="color: #008080;">include</span> <span style="color: #000000;">builtins</span><span style="color: #0000FF;">\</span><span style="color: #000000;">structs</span><span style="color: #0000FF;">.</span><span style="color: #000000;">e</span> <span style="color: #008080;">as</span> <span style="color: #000000;">structs</span>
|
||||
<span style="color: #008080;">constant</span> <span style="color: #000000;">ctx</span> <span style="color: #0000FF;">=</span> <span style="color: #7060A8;">routine_id</span><span style="color: #0000FF;">(</span><span style="color: #008000;">"test"</span><span style="color: #0000FF;">)</span> <span style="color: #000080;font-style:italic;">-- magic/context
|
||||
--constant ctx = "test" -- also works
|
||||
--constant ctx = test -- also works</span>
|
||||
<span style="color: #0000FF;">?</span><span style="color: #000000;">structs</span><span style="color: #0000FF;">:</span><span style="color: #000000;">fetch_field</span><span style="color: #0000FF;">(</span><span style="color: #000000;">t</span><span style="color: #0000FF;">,</span><span style="color: #008000;">"msg"</span><span style="color: #0000FF;">,</span><span style="color: #000000;">ctx</span><span style="color: #0000FF;">)&</span><span style="color: #008000;">" (with some magic)"</span>
|
||||
<span style="color: #000000;">structs</span><span style="color: #0000FF;">:</span><span style="color: #000000;">store_field</span><span style="color: #0000FF;">(</span><span style="color: #000000;">t</span><span style="color: #0000FF;">,</span><span style="color: #008000;">"msg"</span><span style="color: #0000FF;">,</span><span style="color: #008000;">"this breaks privacy"</span><span style="color: #0000FF;">,</span><span style="color: #000000;">ctx</span><span style="color: #0000FF;">)</span>
|
||||
<span style="color: #000000;">t</span><span style="color: #0000FF;">.</span><span style="color: #000000;">show</span><span style="color: #0000FF;">()</span>
|
||||
<!--
|
||||
12
Task/Break-OO-privacy/PicoLisp/break-oo-privacy-1.l
Normal file
12
Task/Break-OO-privacy/PicoLisp/break-oo-privacy-1.l
Normal file
|
|
@ -0,0 +1,12 @@
|
|||
(class +Example)
|
||||
# "_name"
|
||||
|
||||
(dm T (Name)
|
||||
(=: "_name" Name) )
|
||||
|
||||
(dm string> ()
|
||||
(pack "Hello, I am " (: "_name")) )
|
||||
|
||||
(====) # Close transient scope
|
||||
|
||||
(setq Foo (new '(+Example) "Eric"))
|
||||
20
Task/Break-OO-privacy/PicoLisp/break-oo-privacy-2.l
Normal file
20
Task/Break-OO-privacy/PicoLisp/break-oo-privacy-2.l
Normal file
|
|
@ -0,0 +1,20 @@
|
|||
: (string> Foo) # Access via method call
|
||||
-> "Hello, I am Eric"
|
||||
|
||||
: (get Foo '"_name") # Direct access doesn't work
|
||||
-> NIL
|
||||
|
||||
: (get Foo (loc "_name" +Example)) # Locating the transient symbol works
|
||||
-> "Eric"
|
||||
|
||||
: (put Foo (loc "_name" +Example) "Edith")
|
||||
-> "Edith"
|
||||
|
||||
: (string> Foo) # Ditto
|
||||
-> "Hello, I am Edith"
|
||||
|
||||
: (get Foo '"_name")
|
||||
-> NIL
|
||||
|
||||
: (get Foo (loc "_name" +Example))
|
||||
-> "Edith"
|
||||
16
Task/Break-OO-privacy/Python/break-oo-privacy.py
Normal file
16
Task/Break-OO-privacy/Python/break-oo-privacy.py
Normal file
|
|
@ -0,0 +1,16 @@
|
|||
>>> class MyClassName:
|
||||
__private = 123
|
||||
non_private = __private * 2
|
||||
|
||||
|
||||
>>> mine = MyClassName()
|
||||
>>> mine.non_private
|
||||
246
|
||||
>>> mine.__private
|
||||
Traceback (most recent call last):
|
||||
File "<pyshell#23>", line 1, in <module>
|
||||
mine.__private
|
||||
AttributeError: 'MyClassName' object has no attribute '__private'
|
||||
>>> mine._MyClassName__private
|
||||
123
|
||||
>>>
|
||||
6
Task/Break-OO-privacy/Raku/break-oo-privacy.raku
Normal file
6
Task/Break-OO-privacy/Raku/break-oo-privacy.raku
Normal file
|
|
@ -0,0 +1,6 @@
|
|||
class Foo {
|
||||
has $!shyguy = 42;
|
||||
}
|
||||
my Foo $foo .= new;
|
||||
|
||||
say $foo.^attributes.first('$!shyguy').get_value($foo);
|
||||
17
Task/Break-OO-privacy/Ruby/break-oo-privacy.rb
Normal file
17
Task/Break-OO-privacy/Ruby/break-oo-privacy.rb
Normal file
|
|
@ -0,0 +1,17 @@
|
|||
class Example
|
||||
def initialize
|
||||
@private_data = "nothing" # instance variables are always private
|
||||
end
|
||||
private
|
||||
def hidden_method
|
||||
"secret"
|
||||
end
|
||||
end
|
||||
example = Example.new
|
||||
p example.private_methods(false) # => [:hidden_method]
|
||||
#p example.hidden_method # => NoMethodError: private method `name' called for #<Example:0x101308408>
|
||||
p example.send(:hidden_method) # => "secret"
|
||||
p example.instance_variables # => [:@private_data]
|
||||
p example.instance_variable_get :@private_data # => "nothing"
|
||||
p example.instance_variable_set :@private_data, 42 # => 42
|
||||
p example.instance_variable_get :@private_data # => 42
|
||||
13
Task/Break-OO-privacy/Scala/break-oo-privacy.scala
Normal file
13
Task/Break-OO-privacy/Scala/break-oo-privacy.scala
Normal file
|
|
@ -0,0 +1,13 @@
|
|||
class Example(private var name: String) {
|
||||
override def toString = s"Hello, I am $name"
|
||||
}
|
||||
|
||||
object BreakPrivacy extends App {
|
||||
val field = classOf[Example].getDeclaredField("name")
|
||||
field.setAccessible(true)
|
||||
|
||||
val foo = new Example("Erik")
|
||||
println(field.get(foo))
|
||||
field.set(foo, "Edith")
|
||||
println(foo)
|
||||
}
|
||||
15
Task/Break-OO-privacy/Sidef/break-oo-privacy.sidef
Normal file
15
Task/Break-OO-privacy/Sidef/break-oo-privacy.sidef
Normal file
|
|
@ -0,0 +1,15 @@
|
|||
class Example {
|
||||
has public = "foo"
|
||||
method init {
|
||||
self{:private} = "secret"
|
||||
}
|
||||
}
|
||||
|
||||
var obj = Example();
|
||||
|
||||
# Access public attributes
|
||||
say obj.public; #=> "foo"
|
||||
say obj{:public}; #=> "foo"
|
||||
|
||||
# Access private attributes
|
||||
say obj{:private}; #=> "secret"
|
||||
11
Task/Break-OO-privacy/Swift/break-oo-privacy.swift
Normal file
11
Task/Break-OO-privacy/Swift/break-oo-privacy.swift
Normal file
|
|
@ -0,0 +1,11 @@
|
|||
struct Example {
|
||||
var notSoSecret = "Hello!"
|
||||
private var secret = 42
|
||||
}
|
||||
|
||||
let e = Example()
|
||||
let mirror = Mirror(reflecting: e)
|
||||
|
||||
if let secret = mirror.children.filter({ $0.label == "secret" }).first?.value {
|
||||
print("Value of the secret is \(secret)")
|
||||
}
|
||||
11
Task/Break-OO-privacy/Tcl/break-oo-privacy.tcl
Normal file
11
Task/Break-OO-privacy/Tcl/break-oo-privacy.tcl
Normal file
|
|
@ -0,0 +1,11 @@
|
|||
package require Tcl 8.6
|
||||
|
||||
oo::class create Example {
|
||||
variable name
|
||||
constructor n {set name $n}
|
||||
method print {} {puts "Hello, I am $name"}
|
||||
}
|
||||
set e [Example new "Eric"]
|
||||
$e print
|
||||
set [info object namespace $e]::name "Edith"
|
||||
$e print
|
||||
15
Task/Break-OO-privacy/Visual-Basic-.NET/break-oo-privacy.vb
Normal file
15
Task/Break-OO-privacy/Visual-Basic-.NET/break-oo-privacy.vb
Normal file
|
|
@ -0,0 +1,15 @@
|
|||
Imports System.Reflection
|
||||
|
||||
' MyClass is a VB keyword.
|
||||
Public Class MyClazz
|
||||
Private answer As Integer = 42
|
||||
End Class
|
||||
|
||||
Public Class Program
|
||||
Public Shared Sub Main()
|
||||
Dim myInstance = New MyClazz()
|
||||
Dim fieldInfo = GetType(MyClazz).GetField("answer", BindingFlags.NonPublic Or BindingFlags.Instance)
|
||||
Dim answer = fieldInfo.GetValue(myInstance)
|
||||
Console.WriteLine(answer)
|
||||
End Sub
|
||||
End Class
|
||||
10
Task/Break-OO-privacy/Wren/break-oo-privacy.wren
Normal file
10
Task/Break-OO-privacy/Wren/break-oo-privacy.wren
Normal file
|
|
@ -0,0 +1,10 @@
|
|||
class Safe {
|
||||
construct new() { _safe = 42 } // the field _safe is private
|
||||
safe { _safe } // provides public access to field
|
||||
doubleSafe { notSoSafe_ } // another public method
|
||||
notSoSafe_ { _safe * 2 } // intended only for private use but still accesible externally
|
||||
}
|
||||
|
||||
var s = Safe.new()
|
||||
var a = [s.safe, s.doubleSafe, s.notSoSafe_]
|
||||
for (e in a) System.print(e)
|
||||
7
Task/Break-OO-privacy/Zkl/break-oo-privacy.zkl
Normal file
7
Task/Break-OO-privacy/Zkl/break-oo-privacy.zkl
Normal file
|
|
@ -0,0 +1,7 @@
|
|||
class C{var [private] v; fcn [private] f{123} class [private] D {}}
|
||||
C.v; C.f; C.D; // all generate NotFoundError exceptions
|
||||
However:
|
||||
C.fcns //-->L(Fcn(nullFcn),Fcn(f))
|
||||
C.fcns[1]() //-->123
|
||||
C.classes //-->L(Class(D))
|
||||
C.vars //-->L(L("",Void)) (name,value) pairs
|
||||
Loading…
Add table
Add a link
Reference in a new issue