Clarity vs Solidity
Variable Declaration and Mutability
contract User { uint public userAge = 42; function updateAge(uint newAge) public { userAge = newAge; }}
In Solidity, variables are mutable
by default and can be updated directly within functions.
Structs, Tuples, and Maps
contract UserContract { struct User { string name; uint age; } User public user = User("Ryan", 42); function updateUser(string memory newName, uint newAge) public { user.name = newName; user.age = newAge; }}
Solidity uses structs to define custom data types that can group together several variables.
Functions, Modifiers and State Mutability
contract UserManagement { uint private age; function incrementAge() private { age += 1; } function getAge() public view returns (uint) { return age; } function setAge(uint newAge) public { age = newAge; incrementAge(); }}
Solidity uses function modifiers to indicate whether a function can modify the state.
Calling functions
contract UserManagement { uint public age; function setAge(uint newAge) public { age = newAge; }}contract Caller { function callSetAge(address userManagementAddress, uint newAge) public { UserManagement userManagement = UserManagement(userManagementAddress); userManagement.setAge(newAge); }}
In Solidity, functions can be called internally within the contract or externally
by other contracts and transactions.
Events and Logs
contract UserManagement { event UserUpdated(string name, uint age); function updateUser(string memory _name, uint _age) public { emit UserUpdated(_name, _age); }}
In Solidity, events are declared using the event
keyword. You can then emit
your event inside a function to log it.
Access Control
contract Owned { address public owner; constructor() { owner = msg.sender; } modifier onlyOwner() { require(msg.sender == owner, "Not the owner"); _; } function changeOwner(address newOwner) public onlyOwner { owner = newOwner; }}
Solidity allows for the creation of custom modifiers to control access to functions. The onlyOwner
modifier is a common pattern used to restrict function execution to the contract's owner.
Practical Examples
Transferring Native Tokens
contract SendETH { function sendViaTransfer(address payable _to) public payable { _to.transfer(msg.value); }}
To send ETH, you would typically use the transfer
or send
method from an address.
Transferring Fungible Tokens
interface IERC20 { function transfer(address _to, uint256 _amount) external returns (bool);}contract SendERC20 { function transferToken(address _tokenContract, address _to, uint256 _amount) public { IERC20 tokenContract = IERC20(_tokenContract); tokenContract.transfer(_to, _amount); }}
Transferring an ERC20 token in Solidity involves calling the transfer function of the token's contract:
Transferring Non-Fungible Tokens
interface IERC721 { function transferFrom(address _from, address _to, uint256 _tokenId) external;}contract SendERC721 { function transferNFT(address _nftContract, address _to, uint256 _tokenId) public { IERC721 nftContract = IERC721(_nftContract); nftContract.transferFrom(msg.sender, _to, _tokenId); }}
Transferring an ERC721 token (NFT) in Solidity is done using the transferFrom function: