Aqui descreveremos um problema para ser resolvids por algoritmo usando as features de cada linguagem, nesse caso será resolvido nas linguagens Kotlin, Java e Golang.
Neste cenário, temos uma estrutura lógica (observada abaixo), onde recebemos uma relação de pessoas e precisamos retornar uma lista única, ordenada por Estados, em ordem alfabética. Além disso, também só deverão ser retornados os Estados com população igual ou superior à 100 mil habitantes e maiores de 18 anos.
A implementação contém uma classe/função de serviço que implementa a regra e as funções de teste que validam cada um dos cenários abaixo.
Cenário | Entrada | Saída |
---|---|---|
UC_01 | [ Person(name=André Justi, age=null, address=null) ] |
[] |
UC_02 | [ Person(name=André Justi, age=null, address=null), Person(name=Maycow Antunes, age=null, address=null) ] |
[] |
UC_03 | [ Person(name=Paulo Gustavo, age=17, address=Address(street=Doutor Carlos Maia, city=City(name=Cosmopolis, population=100001, state=State(name=SC)))) ] |
[] |
UC_04 | [ Person(name=Wellington Macedo, age=19, address=Address(street=Miguel Dutra, city=City(name=Palhoça, population=99999, state=State(name=SC)))) ] |
[] |
UC_05 | [ Person(name=André Justi, age=28, address=Address(street=Padre Chagas, city=City(name=Florianópolis, population=100001, state=State(name=SC)))) ] |
[SC] |
UC_06 | [ Person(name=André Justi, age=28, address=Address(street=Padre Chagas, city=City(name=Florianópolis, population=100001, state=State(name=SC)))), Person(name=Wellington Macedo, age=19, address=Address(street=Miguel Dutra, city=City(name=Palhoça, population=99999, state=State(name=SC)))), Person(name=Paulo Gustavo, age=19, address=Address(street=Jose Angelo Peti, city=City(name=Druta, population=99999, state=State(name=SP)))), Person(name=Maycow Antunes, age=19, address=Address(street=Dona Ema, city=City(name=Rio Negrinho, population=100001, state=State(name=RJ)))) ] |
[RJ, SC] |
UC_07 | [] | [] |
package com.mercadolibre.examples.kotlin
import org.junit.jupiter.api.Assertions
import org.junit.jupiter.api.Test
data class State(val name: String? = null)
data class City(val name: String? = null, val population: Int? = null, val state: State? = null)
data class Address(val street: String? = null, val city: City? = null)
data class Person(val name: String? = null, val age: Int? = null, val address: Address? = null)
class PersonService {
companion object {
const val AGE_LIMIT_FILTER = 18
const val POPULATION_LIMIT_FILTER = 100000
}
fun getStates(persons: Collection<Person>) = persons
.filter { it.age ?: 0 >= AGE_LIMIT_FILTER }
.mapNotNull(Person::address)
.mapNotNull(Address::city)
.filter { it.population ?: 0 >= POPULATION_LIMIT_FILTER }
.mapNotNull(City::state)
.mapNotNull(State::name)
.distinct()
.sorted()
}
class UC {
private val personService = PersonService()
@Test
fun `UC_01`() {
val persons = listOf(
Person(name = "André Justi", age = null, address = null)
)
val states = personService.getStates(persons)
Assertions.assertTrue(states.isEmpty())
}
@Test
fun `UC_02`() {
val persons = listOf(
Person(name = "André Justi", age = null, address = null),
Person(name = "Maycow Antunes", age = null, address = null)
)
val states = personService.getStates(persons)
Assertions.assertTrue(states.isEmpty())
}
@Test
fun `UC_03`() {
val persons = listOf(
Person(name = "Paulo Gustavo", age = PersonService.AGE_LIMIT_FILTER - 1, address = Address(street = "Doutor Carlos Maia", city = City(name = "Cosmopolis", population = PersonService.POPULATION_LIMIT_FILTER + 1, state = State(name = "SC"))))
)
val states = personService.getStates(persons)
Assertions.assertTrue(states.isEmpty())
}
@Test
fun `UC_04`() {
val persons = listOf(
Person(name = "Wellington Macedo", age = PersonService.AGE_LIMIT_FILTER + 1, address = Address(street = "Miguel Dutra", city = City(name = "Palhoça", population = PersonService.POPULATION_LIMIT_FILTER - 1, state = State(name = "SC"))))
)
val states = personService.getStates(persons)
Assertions.assertTrue(states.isEmpty())
}
@Test
fun `UC_05`() {
val persons = listOf(
Person(name = "André Justi", age = PersonService.AGE_LIMIT_FILTER + 10, address = Address(street = "Padre Chagas", city = City(name = "Florianópolis", population = PersonService.POPULATION_LIMIT_FILTER + 1, state = State(name = "SC"))))
)
val states = personService.getStates(persons)
Assertions.assertEquals(listOf("SC"), states)
}
@Test
fun `UC_06`() {
val persons = listOf(
Person(name = "André Justi", age = PersonService.AGE_LIMIT_FILTER + 10, address = Address(street = "Padre Chagas", city = City(name = "Florianópolis", population = PersonService.POPULATION_LIMIT_FILTER + 1, state = State(name = "SC")))),
Person(name = "Wellington Macedo", age = PersonService.AGE_LIMIT_FILTER + 1, address = Address(street = "Miguel Dutra", city = City(name = "Palhoça", population = PersonService.POPULATION_LIMIT_FILTER - 1, state = State(name = "SC")))),
Person(name = "Paulo Gustavo", age = PersonService.AGE_LIMIT_FILTER + 1, address = Address(street = "Jose Angelo Peti", city = City(name = "Druta", population = PersonService.POPULATION_LIMIT_FILTER - 1, state = State(name = "SP")))),
Person(name = "Maycow Antunes", age = PersonService.AGE_LIMIT_FILTER + 1, address = Address(street = "Dona Ema", city = City(name = "Rio Negrinho", population = PersonService.POPULATION_LIMIT_FILTER + 1, state = State(name = "RJ"))))
)
val states = personService.getStates(persons)
Assertions.assertEquals(listOf("RJ", "SC"), states)
}
@Test
fun `UC_07`() {
val persons = emptyList<Person>()
val states = personService.getStates(persons)
Assertions.assertTrue(states.isEmpty())
}
}
import (
"sort"
"testing"
"github.com/stretchr/testify/assert"
)
type State struct {
Name string
}
type City struct {
Name string
Population int
State *State
}
type Address struct {
Street string
City *City
}
type Person struct {
Name string
Age int
Address *Address
}
const (
AgeLimitFilter = 18
PopulationLimitFilter = 100000
)
func getStates(persons []Person) (states []string) {
for _, person := range persons {
if !isPersonOlderThanLimit(person) {
continue
}
stateName := getStateNameByPersonAndPopulationGreaterLimit(person)
if stateName==""{
continue
}
if !containsElementInSlice(states, stateName){
states = append(states, stateName)
}
}
sort.Strings(states)
return states
}
func containsElementInSlice(slices []string, element string) bool{
for _,v := range slices{
if v==element{
return true
}
}
return false
}
func isPersonOlderThanLimit(person Person) bool {
return person.Age >= AgeLimitFilter
}
func getStateNameByPersonAndPopulationGreaterLimit(person Person) string {
address := person.Address
if address == nil {
return ""
}
city := address.City
if city == nil || city.Population < PopulationLimitFilter {
return ""
}
if city.State == nil {
return ""
}
return city.State.Name
}
func Test_UC_01(t *testing.T) {
persons := []Person{
{Name: "André Justi"},
}
states := getStates(persons)
assert.Empty(t, states)
}
func Test_UC_02(t *testing.T) {
persons := []Person{
{Name: "André Justi"},
{Name: "Maycow Antunes"},
}
states := getStates(persons)
assert.Empty(t, states)
}
func Test_UC_03(t *testing.T) {
persons := []Person{
{Name: "Paulo Gustavo", Age: AgeLimitFilter - 1, Address: &Address{Street: "Doutor Carlos Maia", City: &City{Name: "Cosmopolis", Population: PopulationLimitFilter + 1, State: &State{Name: "SC"}}}},
}
states := getStates(persons)
assert.Empty(t, states)
}
func Test_UC_04(t *testing.T) {
persons := []Person{
{Name: "Wellington Macedo", Age: AgeLimitFilter + 1, Address: &Address{Street: "Miguel Dutra", City: &City{Name: "Palhoça", Population: PopulationLimitFilter - 1, State: &State{Name: "SC"}}}},
}
states := getStates(persons)
assert.Empty(t, states)
}
func Test_UC_05(t *testing.T) {
persons := []Person{
{Name: "André Justi", Age: AgeLimitFilter + 10, Address: &Address{Street: "Padre Chagas", City: &City{Name: "Florianópolis", Population: PopulationLimitFilter + 1, State: &State{Name: "SC"}}}},
}
states := getStates(persons)
assert.Equal(t, []string{"SC"}, states)
}
func Test_UC_06(t *testing.T) {
persons := []Person{
{Name: "André Justi", Age: AgeLimitFilter + 10, Address: &Address{Street: "Padre Chagas", City: &City{Name: "Florianópolis", Population: PopulationLimitFilter + 1, State: &State{Name: "SC"}}}},
{Name: "Wellington Macedo", Age: AgeLimitFilter + 1, Address: &Address{Street: "Miguel Dutra", City: &City{Name: "Palhoça", Population: PopulationLimitFilter - 1, State: &State{Name: "SC"}}}},
{Name: "Paulo Gustavo", Age: AgeLimitFilter + 1, Address: &Address{Street: "Jose Angelo Peti", City: &City{Name: "Druta", Population: PopulationLimitFilter - 1, State: &State{Name: "SP"}}}},
{Name: "Maycow Antunes", Age: AgeLimitFilter + 1, Address: &Address{Street: "Dona Ema", City: &City{Name: "Rio Negrinho", Population: PopulationLimitFilter + 1, State: &State{Name: "RJ"}}}},
}
states := getStates(persons)
assert.Equal(t, []string{"RJ", "SC"}, states)
}
func Test_UC_07(t *testing.T) {
var persons []Person
states := getStates(persons)
assert.Empty(t, states)
}
package com.mercadolibre.examples.java;
import org.junit.jupiter.api.Assertions;
import org.junit.jupiter.api.Test;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Collection;
import java.util.stream.Collectors;
class State {
private final String name;
public State(String name) {
this.name = name;
}
public String getName() {
return name;
}
}
class City {
private final String name;
private final Integer population;
private final State state;
public City(String name, Integer population, State state) {
this.name = name;
this.population = population;
this.state = state;
}
public String getName() {
return name;
}
public Integer getPopulation() {
return population;
}
public State getState() {
return state;
}
}
class Address {
private final String street;
private final City city;
public Address(String street, City city) {
this.street = street;
this.city = city;
}
public String getStreet() {
return street;
}
public City getCity() {
return city;
}
}
class Person {
private final String name;
private final Integer age;
private final Address address;
public Person(String name, Integer age, Address address) {
this.name = name;
this.age = age;
this.address = address;
}
public String getName() {
return name;
}
public Address getAddress() {
return address;
}
public Integer getAge() {
return age;
}
}
class PersonService {
public static final Integer AGE_LIMIT_FILTER = 18;
public static final Integer POPULATION_LIMIT_FILTER = 100000;
public Collection<String> getStates(Collection<Person> persons) {
if (persons == null) {
return new ArrayList<>();
}
return persons.stream()
.filter(person -> person.getAge() != null && person.getAge() >= AGE_LIMIT_FILTER)
.map(Person::getAddress)
.map(Address::getCity)
.filter(city -> city.getPopulation() != null && city.getPopulation() >= POPULATION_LIMIT_FILTER)
.map(City::getState)
.map(State::getName)
.distinct()
.sorted()
.collect(Collectors.toList());
}
}
public class UC {
private PersonService personService = new PersonService();
@Test
public void UC_01() {
Collection<Person> persons = Arrays.asList(
new Person("André Justi", null, null)
);
Collection<String> states = personService.getStates(persons);
Assertions.assertTrue(states.isEmpty());
}
@Test
public void UC_02() {
Collection<Person> persons = Arrays.asList(
new Person("André Justi", null, null),
new Person("Maycow Antunes", null, null)
);
Collection<String> states = personService.getStates(persons);
Assertions.assertTrue(states.isEmpty());
}
@Test
public void UC_03() {
Collection<Person> persons = Arrays.asList(
new Person("Paulo Gustavo", PersonService.AGE_LIMIT_FILTER - 1, new Address("Doutor Carlos Maia", new City("Cosmopolis", PersonService.POPULATION_LIMIT_FILTER + 1, new State("SC"))))
);
Collection<String> states = personService.getStates(persons);
Assertions.assertTrue(states.isEmpty());
}
@Test
public void UC_04() {
Collection<Person> persons = Arrays.asList(
new Person("Wellington Macedo", PersonService.AGE_LIMIT_FILTER + 1, new Address("Miguel Dutra", new City("Palhoça", PersonService.POPULATION_LIMIT_FILTER - 1, new State("SC"))))
);
Collection<String> states = personService.getStates(persons);
Assertions.assertTrue(states.isEmpty());
}
@Test
public void UC_05() {
Collection<Person> persons = Arrays.asList(
new Person("André Justi", PersonService.AGE_LIMIT_FILTER + 10, new Address("Padre Chagas", new City("Florianópolis", PersonService.POPULATION_LIMIT_FILTER + 1, new State("SC"))))
);
Collection<String> states = personService.getStates(persons);
Assertions.assertEquals(Arrays.asList("SC"), states);
}
@Test
public void UC_06() {
Collection<Person> persons = Arrays.asList(
new Person("André Justi", PersonService.AGE_LIMIT_FILTER + 10, new Address("Padre Chagas", new City("Florianópolis", PersonService.POPULATION_LIMIT_FILTER + 1, new State("SC")))),
new Person("Wellington Macedo", PersonService.AGE_LIMIT_FILTER + 1, new Address("Miguel Dutra", new City("Palhoça", PersonService.POPULATION_LIMIT_FILTER - 1, new State("SC")))),
new Person("Paulo Gustavo", PersonService.AGE_LIMIT_FILTER + 1, new Address("Jose Angelo Peti", new City("Druta", PersonService.POPULATION_LIMIT_FILTER - 1, new State("SP")))),
new Person("Maycow Antunes", PersonService.AGE_LIMIT_FILTER + 1, new Address("Dona Ema", new City("Rio Negrinho", PersonService.POPULATION_LIMIT_FILTER + 1, new State("RJ"))))
);
Collection<String> states = personService.getStates(persons);
Assertions.assertEquals(Arrays.asList("RJ", "SC"), states);
}
@Test
public void UC_07() {
Collection<Person> persons = Arrays.asList();
Collection<String> states = personService.getStates(persons);
Assertions.assertTrue(states.isEmpty());
}
}