Решение на Matrix 4 от Цветелина Чакърова

Обратно към всички решения

Към профила на Цветелина Чакърова

Резултати

  • 20 точки от тестове
  • 0 бонус точки
  • 20 точки общо
  • 15 успешни тест(а)
  • 0 неуспешни тест(а)

Код

use std::ops::Add;
use std::ops::Mul;
use std::iter;
#[derive(Debug)]
pub struct Matrix<T: Clone> {
element11 : T,
element12 : T,
element21 : T,
element22 : T,
}
#[derive(Debug, Clone, PartialEq)]
pub struct Cell<T>(pub T);
impl<T: Clone> Matrix<T> {
pub fn new(data: &[T; 4]) -> Matrix<T> {
let matrix = Matrix {
element11 : data[0].clone(),
element12 : data[1].clone(),
element21 : data[2].clone(),
element22 : data[3].clone(),
};
matrix
}
pub fn by_row(&self) -> Vec<Cell<T>> {
let mut vec_by_row: Vec<Cell<T>> = Vec::new();
vec_by_row.push(Cell::<T>(self.element11.clone()));
vec_by_row.push(Cell::<T>(self.element12.clone()));
vec_by_row.push(Cell::<T>(self.element21.clone()));
vec_by_row.push(Cell::<T>(self.element22.clone()));
vec_by_row
}
pub fn by_col(&self) -> Vec<Cell<T>> {
let mut vec_by_col: Vec<Cell<T>> = Vec::new();
vec_by_col.push(Cell::<T>(self.element11.clone()));
vec_by_col.push(Cell::<T>(self.element21.clone()));
vec_by_col.push(Cell::<T>(self.element12.clone()));
vec_by_col.push(Cell::<T>(self.element22.clone()));
vec_by_col
}
}
impl Add<Cell<String>> for Cell<i32> {
type Output = Cell<String>;
fn add(self, other: Cell<String>) -> Cell<String> {
if self.0 >= 0 { Cell(self.0.to_string() + &String::from(" ") + &other.0) }
else { let mut reversed = String::new();
for character in other.0.chars().rev() {
reversed.push(character)
}
Cell(reversed + &String::from(" ") + &(-1 * self.0).to_string())
}
}
}
impl Mul<Cell<String>> for Cell<i32> {
type Output = Cell<String>;
fn mul(self, other: Cell<String>) -> Cell<String> {
if self.0 == 0 {
Cell(String::from(""))
}
else {
if self.0 < 0 {
let mut reversed = String::new();
for character in other.0.chars().rev() {
reversed.push(character)
}
let mut reversedMultiplied: String = reversed.clone();
let mut counter = (-1 * self.0) - 1;
while (counter > 0) {
reversedMultiplied += &reversed.clone();
counter -= 1;
}
Cell(reversedMultiplied)
}
else {
let mut multiplied = String::new();
for index in 0..self.0 {
multiplied += &other.0;
}
Cell(multiplied)
}
}
}
}
impl Add<Matrix<String>> for Matrix<i32> {
type Output = Matrix<String>;
fn add(self, other: Matrix<String>) -> Matrix<String> {
let element11_result : String;
let element12_result : String;
let element21_result : String;
let element22_result : String;
if self.element11.clone() >= 0 { element11_result = self.element11.clone().to_string() + &String::from(" ") + &other.element11;}
else { let mut reversed = String::new();
for character in other.element11.chars().rev() {
reversed.push(character)
}
element11_result = reversed + &String::from(" ") + &(-1 * self.element11.clone()).to_string();
}
if self.element12.clone() >= 0 { element12_result = self.element12.clone().to_string() + &String::from(" ") + &other.element12;}
else { let mut reversed = String::new();
for character in other.element12.chars().rev() {
reversed.push(character)
}
element12_result = reversed + &String::from(" ") + &(-1 * self.element12.clone()).to_string();
}
if self.element21.clone() >= 0 { element21_result = self.element21.clone().to_string() + &String::from(" ") + &other.element21;}
else { let mut reversed = String::new();
for character in other.element21.chars().rev() {
reversed.push(character)
}
element21_result = reversed + &String::from(" ") + &(-1 * self.element21.clone()).to_string();
}
if self.element22.clone() >= 0 { element22_result = self.element22.clone().to_string() + &String::from(" ") + &other.element22;}
else { let mut reversed = String::new();
for character in other.element22.chars().rev() {
reversed.push(character)
}
element22_result = reversed + &String::from(" ") + &(-1 * self.element22.clone()).to_string();
}
let matrix = Matrix {
element11 : element11_result.clone(),
element12 : element12_result.clone(),
element21 : element21_result.clone(),
element22 : element22_result.clone(),
};
matrix
}
}
impl Mul<Matrix<String>> for Matrix<i32> {
type Output = String;
fn mul(self, other: Matrix<String>) -> String {
let element11_11_result : String;
let element21_12_result : String;
let element12_21_result : String;
let element22_22_result : String;
let result : String;
if self.element11 == 0 {element11_11_result = String::from("");}
else { if self.element11 > 0 {
let mut multiplied = String::new();
for index in 0..self.element11 {
multiplied += &other.element11;
}
element11_11_result = multiplied;
}
else {
let mut reversed = String::new();
for character in other.element11.chars().rev() {
reversed.push(character)
}
let mut reversedMultiplied: String = reversed.clone();
let mut counter = (-1 * self.element11) - 1;
while (counter > 0) {
reversedMultiplied += &reversed.clone();
counter -= 1;
}
element11_11_result = reversedMultiplied;
}
}
if self.element21 == 0 {element21_12_result = String::from("");}
else { if self.element21 > 0 {
let mut multiplied = String::new();
for index in 0..self.element21 {
multiplied += &other.element12;
}
element21_12_result = multiplied;
}
else {
let mut reversed = String::new();
for character in other.element12.chars().rev() {
reversed.push(character)
}
let mut reversedMultiplied: String = reversed.clone();
let mut counter = (-1 * self.element21) - 1;
while (counter > 0) {
reversedMultiplied += &reversed.clone();
counter -= 1;
}
element21_12_result = reversedMultiplied;
}
}
if self.element12 == 0 {element12_21_result = String::from("");}
else { if self.element12 > 0 {
let mut multiplied = String::new();
for index in 0..self.element12 {
multiplied += &other.element21;
}
element12_21_result = multiplied;
}
else {
let mut reversed = String::new();
for character in other.element21.chars().rev() {
reversed.push(character)
}
let mut reversedMultiplied: String = reversed.clone();
let mut counter = (-1 * self.element12) - 1;
while (counter > 0) {
reversedMultiplied += &reversed.clone();
counter -= 1;
}
element12_21_result = reversedMultiplied;
}
}
if self.element22 == 0 {element22_22_result = String::from("");}
else { if self.element22 > 0 {
let mut multiplied = String::new();
for index in 0..self.element22 {
multiplied += &other.element22;
}
element22_22_result = multiplied;
}
else {
let mut reversed = String::new();
for character in other.element22.chars().rev() {
reversed.push(character)
}
let mut reversedMultiplied: String = reversed.clone();
let mut counter = (-1 * self.element22) - 1;
while (counter > 0) {
reversedMultiplied += &reversed.clone();
counter -= 1;
}
element22_22_result = reversedMultiplied;
}
}
result = element11_11_result + &String::from(" ") + &element12_21_result + &String::from(" ") + &element21_12_result
+ &String::from(" ") + &element22_22_result;
result
}
}

Лог от изпълнението

Compiling solution v0.1.0 (/tmp/d20220112-2706256-1wfdkt3/solution)
warning: unused import: `std::iter`
 --> src/lib.rs:3:5
  |
3 | use std::iter;
  |     ^^^^^^^^^
  |
  = note: `#[warn(unused_imports)]` on by default

warning: unnecessary parentheses around `while` condition
  --> src/lib.rs:82:19
   |
82 |             while (counter > 0) {
   |                   ^^^^^^^^^^^^^ help: remove these parentheses
   |
   = note: `#[warn(unused_parens)]` on by default

warning: unnecessary parentheses around `while` condition
   --> src/lib.rs:181:27
    |
181 |                     while (counter > 0) {
    |                           ^^^^^^^^^^^^^ help: remove these parentheses

warning: unnecessary parentheses around `while` condition
   --> src/lib.rs:206:27
    |
206 |                     while (counter > 0) {
    |                           ^^^^^^^^^^^^^ help: remove these parentheses

warning: unnecessary parentheses around `while` condition
   --> src/lib.rs:231:27
    |
231 |                     while (counter > 0) {
    |                           ^^^^^^^^^^^^^ help: remove these parentheses

warning: unnecessary parentheses around `while` condition
   --> src/lib.rs:256:27
    |
256 |                     while (counter > 0) {
    |                           ^^^^^^^^^^^^^ help: remove these parentheses

warning: unused variable: `index`
  --> src/lib.rs:91:21
   |
91 |                 for index in 0..self.0 {
   |                     ^^^^^ help: if this is intentional, prefix it with an underscore: `_index`
   |
   = note: `#[warn(unused_variables)]` on by default

warning: unused variable: `index`
   --> src/lib.rs:168:25
    |
168 |                     for index in 0..self.element11 {
    |                         ^^^^^ help: if this is intentional, prefix it with an underscore: `_index`

warning: unused variable: `index`
   --> src/lib.rs:193:25
    |
193 |                     for index in 0..self.element21 {
    |                         ^^^^^ help: if this is intentional, prefix it with an underscore: `_index`

warning: unused variable: `index`
   --> src/lib.rs:218:25
    |
218 |                     for index in 0..self.element12 {
    |                         ^^^^^ help: if this is intentional, prefix it with an underscore: `_index`

warning: unused variable: `index`
   --> src/lib.rs:243:25
    |
243 |                     for index in 0..self.element22 {
    |                         ^^^^^ help: if this is intentional, prefix it with an underscore: `_index`

warning: variable `reversedMultiplied` should have a snake case name
  --> src/lib.rs:80:21
   |
80 |             let mut reversedMultiplied: String = reversed.clone();
   |                     ^^^^^^^^^^^^^^^^^^ help: convert the identifier to snake case: `reversed_multiplied`
   |
   = note: `#[warn(non_snake_case)]` on by default

warning: variable `reversedMultiplied` should have a snake case name
   --> src/lib.rs:179:29
    |
179 |                     let mut reversedMultiplied: String = reversed.clone();
    |                             ^^^^^^^^^^^^^^^^^^ help: convert the identifier to snake case: `reversed_multiplied`

warning: variable `reversedMultiplied` should have a snake case name
   --> src/lib.rs:204:29
    |
204 |                     let mut reversedMultiplied: String = reversed.clone();
    |                             ^^^^^^^^^^^^^^^^^^ help: convert the identifier to snake case: `reversed_multiplied`

warning: variable `reversedMultiplied` should have a snake case name
   --> src/lib.rs:229:29
    |
229 |                     let mut reversedMultiplied: String = reversed.clone();
    |                             ^^^^^^^^^^^^^^^^^^ help: convert the identifier to snake case: `reversed_multiplied`

warning: variable `reversedMultiplied` should have a snake case name
   --> src/lib.rs:254:29
    |
254 |                     let mut reversedMultiplied: String = reversed.clone();
    |                             ^^^^^^^^^^^^^^^^^^ help: convert the identifier to snake case: `reversed_multiplied`

warning: `solution` (lib) generated 16 warnings
    Finished test [unoptimized + debuginfo] target(s) in 7.63s
     Running tests/solution_test.rs (target/debug/deps/solution_test-4c880d3f0adaac34)

running 15 tests
test solution_test::test_adding_int_and_string_negative ... ok
test solution_test::test_adding_int_and_string_positive ... ok
test solution_test::test_adding_int_and_string_unicode ... ok
test solution_test::test_adding_int_and_string_zero ... ok
test solution_test::test_adding_matrices_1 ... ok
test solution_test::test_adding_matrices_2 ... ok
test solution_test::test_blank_strings ... ok
test solution_test::test_iterating_i32s ... ok
test solution_test::test_iterating_strings ... ok
test solution_test::test_multiplying_int_and_string_negative ... ok
test solution_test::test_multiplying_int_and_string_positive ... ok
test solution_test::test_multiplying_int_and_string_unicode ... ok
test solution_test::test_multiplying_int_and_string_zero ... ok
test solution_test::test_multiplying_matrices_1 ... ok
test solution_test::test_multiplying_matrices_2 ... ok

test result: ok. 15 passed; 0 failed; 0 ignored; 0 measured; 0 filtered out; finished in 0.01s

История (1 версия и 1 коментар)

Цветелина качи първо решение на 17.11.2021 23:47 (преди почти 4 години)

Идеята на това да имплементирате първо събиране и умножение на клетки, а после на матрици, беше да преизползвате операциите за клетки в операциите за матрици. Ти вместо това си копирала кода от едно място на всички други. Проблема с това е, че ако случайно намериш проблем, сега трябва да оправиш абсолютно всички други места, на които си копирала същия код.

Примерно, ето как би могло да изглежда събирането на матрици в твоето решение, стига да преизползваш събирането на клетки:

impl Add<Matrix<String>> for Matrix<i32> {
    type Output = Matrix<String>;
    fn add(self, other: Matrix<String>) -> Matrix<String> {
        let element11_result = (Cell(self.element11.clone()) + Cell(other.element11.clone())).0;
        let element12_result = (Cell(self.element12.clone()) + Cell(other.element12.clone())).0;
        let element21_result = (Cell(self.element21.clone()) + Cell(other.element21.clone())).0;
        let element22_result = (Cell(self.element22.clone()) + Cell(other.element22.clone())).0;

        Matrix {
            element11 : element11_result,
            element12 : element12_result,
            element21 : element21_result,
            element22 : element22_result,
        }
    }
}

Може да изглежда и по-кратко даже -- няма нужда от временните "result" променливи. Но дори и това съкращава твоите 53 реда на 16, като кода е доста по-четим, защото нямаш нужда да разбираш какво прави всеки индивидуален блок код.

Разгледай останалите решения и виж как са решили проблема колегите, какво са преизползвали и какво са копирали. Виж и моето решение, макар че аз съм използвал малко по-засукани итератори за събирането и умножението.

Добра идея е и да опиташ да си форматираш кода по-прилежно. Rust компилатора хвърля доста warning-и за излишни скоби, имената на променливите и индентацията също са доста неконсистентни. Прилежно написания код се и чете по-лесно. Може да пробваш rustfmt като някакъв по-автоматизиран начин да ти се преподреди малко кода.