What is the difference between a DBMS and an RDBMS with some examples and some new tools as examples. Why can't we really use a DBMS instead of an RDBMS or vice versa?
A relational DBMS will expose to its users "relations, and nothing else". Other DBMS's will violate that principle in various ways. E.g. in IDMS, you could do <ACCEPT <hostvar> FROM CURRENCY> and this would expose the internal record id of the "current record" to the user, violating the "nothing else".
A relational DBMS will allow its users to operate exclusively at the logical level, i.e. work exclusively with assertions of fact (which are represented as tuples). Other DBMS's made/make their users operate more at the "record" level (too "low" on the conceptual-logical-physical scale) or at the "document" level (in a certain sense too "high" on that same scale, since a "document" is often one particular view of a multitude of underlying facts).
A relational DBMS will also offer facilities for manipulation of the data, in the form of a language that supports the operations of the relational algebra. Other DBMS's, seeing as they don't support relations to boot, obviously cannot build their data manipulation facilities on relational algebra, and as a consequence the data manipulation facilities/language is mostly ad-hoc. On the "too low" end of the spectrum, this forces DBMS users to hand-write operations such as JOIN again and again and again. On the "too high" end of the spectrum, it causes problems of combinatorial explosion in language complexity/size (the RA has some 4 or 5 primitive operators and that's all it needs - can you imagine 4 or 5 operators that will allow you to do just any "document transform" anyone would ever want to do ?)
(Note very carefully that even SQL systems violate basic relational principles quite seriously, so "relational DBMS" is a thing that arguably doesn't even exist, except then in rather small specialized spaces, see e.g. http://www.thethirdmanifesto.com/ - projects page.)
DBMS : Database management system, here we can store some data and collect.
Imagine a single table , save and read.
RDBMS : Relational Database Management , here you can join several tables together and get related data and queried data ( say data for a particular user or for an particular order,not all users or all orders)
The Noramalization forms comes into play in RDBMS, we dont need to store repeated data again and again, can store in one table, and use the id in other table, easier to update, and for reading we can join both the table and get what we want.
DBMS:
DBMS applications store data as file.In DBMS, data is generally stored in either a hierarchical form or a navigational form.Normalization is not present in DBMS.
RDBMS:
RDBMS applications store data in a tabular form.In RDBMS, the tables have an identifier called primary key and the data values are stored in the form of tables.Normalization is present in RDBMS.
Related
I have picked up the book named "Fundamentals of Database Systems, 3rd Edition" by Elmasri and Navathe to get a basic understanding first. I have started reading it from the first chapter.
A database is a logically coherent collection of data with some
inherent meaning, representing some aspect of real world and which is
designed, built and populated with data for a specific purpose.
What does means above paragraph?
A database is seen as a particular perspective on data and its representation in a framework of well-defined structures and interdependencies.
Breaking the definition down into parts:
'collection of data':
What it's all about.
'with some inherent meaning':
Mostly tautological, it would not constitute data otherwise. It shows, however, that databases do not exist to elicit the meaning of data. They may aid in doing so, though.
'representing some aspect of real world':
Contestable, as databases may represent data over abstract domains like mathematics ( eg. a database of prime number twins ). Unless this also counts as 'real world', which would make this part tautological.
'logically coherent':
Data items are related in a non-arbitrary way that allows reasoning about them. Often this aspect also includes comprehensiveness (as an objective at least) for the purpose at hand.
'for a specific purpose':
The intended perspective on the data, which co-determines the nature of structures and relationships the database will be composed of.
In particular the choice of representations and abstractions applied (eg. which parts of available data are dropped) depend on the intended purpose.
'designed, built and populated with data':
Implies that databases comprise a model and use a technical base. It also implies that databases focus on the description of data.
The usefulness of such high-level descriptions is probably limited but may help to focus on some key issues wrt databases:
- Describing data \
- Structuring data > modelling data
- Relating data items to each other /
- Reasoning over data
- Databases are tools
My teacher wrote the answer for what is database in the slides, it says this
Database:
a collection of data
represents some aspect of the real world (database represent something in the real world)
logically coherent collection (not a random collection)
designed, built & populated for a specific purpose
I thought at first that it isn't a relational DB, but after I read that I can join tables and it was written on their site https://crate.io/overview/ (see Use cases), I'm not sure.
Especially I got confused by the senctence:
CrateDB is based on a NoSQL architecture, but features standard SQL.
from https://crate.io/overview/high-level-architecture/
Going by a Codd's 12 rules (which have been used to identify relational databases), CrateDB is not a relational database - yet. CrateDB's eventual consistency model does not prohibit that.
Rule 0: For any system that is advertised as, or claimed to be, a relational data base management system, that system must be able to manage data bases entirely through its relational capabilities.
CrateDB doesn't have another interface with which data can be inserted, retrieved, and updated.
Rule 1: All information in a relational data base is represented explicitly at the logical level and in exactly one way — by values in tables.
Exactly what can be found in CrateDB.
Rule 2: Each and every datum (atomic value) in a relational data base is guaranteed to be logically accessible by resorting to a combination of table name, primary key value and column name.
This is strictly enforced. Access through primary keys will even give you read-after-write consistency.
Rule 3: Null values (distinct from the empty character string or a string of blank characters and distinct from zero or any other number) are supported in fully relational DBMS for representing missing information and inapplicable information in a systematic way, independent of data type.
CrateDB supports null.
Rule 4: The data base description is represented at the logical level in the same way as ordinary data, so that authorized users can apply the same relational language to its interrogation as they apply to the regular data.
CrateDB has among other meta-tables, Information Schema tables
Rule 5: A relational system may support several languages and various modes of terminal use (for example, the fill-in-the-blanks mode). However, there must be at least one language whose statements are expressible, per some well-defined syntax, as character strings and that is comprehensive in supporting all of the following items:
Data definition.
View definition.
Data manipulation (interactive and by program).
Integrity constraints.
Authorization.
Transaction boundaries (begin, commit and rollback).
CrateDB supports data definition and data manipulation parts and only a single integrity constraint (primary key). This is definitely incomplete.
Rule 6: All views that are theoretically updatable are also updatable by the system.
CrateDB does not support views yet.
Rule 7: The capability of handling a base relation or a derived relation as a single operand applies not only to the retrieval of data but also to the insertion, update and deletion of data.
CrateDB currently only does that for data retrieval...
Rule 8: Application programs and terminal activities remain logically unimpared whenever any changes are made in either storage representations or access methods.
CrateDB's use of SQL allows for this; performance/storage level improvements are even delivered via system upgrades.
Rule 9: Application programs and terminal activites remain logically unimpared when information-preserving changes of any kind that theoretically permit unimpairment are made to the base tables.
Parts of this are still missing (the views, inserts/updates on joins). However for retrieving data, this is already the case.
Rule 10: Integrity constraints specific to a particular relational data base must be definable in the relational data sublanguage and storable in the catalog, not in the application programs.
This is quite tricky for a distributed database, specifically the foreign key constraints. CrateDB only supports primary key constraints for now.
Rule 11: A relational DBMS has distribution independence.
In CrateDB any kind of sharding/partitioning/distribution is handled transparently for the user. Any kinds of constraints/settings for data distribution are applied on the data definition level.
Rule 12: If a relational system has a low-level (single-record-at-a-time) language, that low level cannot be used to subvert or bypass the integrity rules and constraints expressed in the higher level relational language (multiple-records-at-a-time).
One could argue that COPY FROM directly violates this rule since there is no type checking and conversion happening underneath. However there is no other command/language/API that would allow data manipulation otherwise.
While CrateDB certainly has some catching up to do, there is no reason why it wouldn't become a relational database in this sense soon. Its SQL support may not be on par with Oracle's or Postgres' but many people can live without some very use-case specific features.
As said above, all of the rules above are not directly violated, but rather not implemented yet in a satisfactory manner, so there is no reason why CrateDB can't become a fully relational database eventually.
(Disclaimer: I work there)
Since the beginning of the relational model the three main components that a system must have to be considered relational are (applying Codd's three-component definition of "data model" to the relational model):
data is presented as relations (tables)
manipulation is via relation and/or logic operators/expressions
integrity is enforced by relation and/or logic operators/expressions
Also a multi-user DMBS has been understood to support apparently atomic persistent transactions while benefiting from implementation via overlapped execution (ACID) and a distributed DBMS has been understood to support an apparent single database while benefiting from implementation at multiple sites.
By these criteria CrateDB is not relational.
It has tables, but its manipulation of tables in extremely limited and it has almost no integrity functionality. Re manipulation, it allows querying for rows of a table meeting a condition (including aggregation), and it allows joining multiple tables, but that's not optimized, even for equijoin. Re constraints, its only functionality is column typing, primary keys and non-null columns. It uses a tiny subset of SQL.
See the pages at your link re Supported Features and Standard SQL Compliance as addressed in:
Crate SQL
Data Definition
Constraints (PRIMARY KEY Constraint, NOT NULL Constraint)
Indices
Data Manipulation
Querying Crate
Retrieving Data (FROM Clause, Joins)
Joins
Crate SQL Syntax Reference
As usual with non-relational DBMSs, their documentation does not reflect an understanding or appreciation of the relational model or other fundamental DBMS functionality.
CrateDB is a distributed SQL database. The underlying technology is similar to what so called NoSQL databases typically use (shared nothing architecture, columnar indexes, eventual-consistency, support for semi-structured records) - but makes it accessible via a traditional SQL interface.
So therefor - YES, CrateDB is somewhat of a relational SQL DB.
I have a legacy in-house human resources web app that I'd like to rebuild using more modern technologies. Doctrine 2 is looking good. But I've not been able to find articles or documentation on how best to organise the Entities for a large-ish database (120 tables). Can you help?
My main problem is the Person table (of course! it's an HR system!). It currently has 70 columns. I want to refactor that to extract several subsets into one-to-one sub tables, which will leave me with about 30 columns. There are about 50 other supporting one-to-many tables called person_address, person_medical, person_status, person_travel, person_education, person_profession etc. More will be added later.
If I put all the doctrine associations (http://docs.doctrine-project.org/projects/doctrine-orm/en/latest/reference/working-with-associations.html) in the Person entity class along with the set/get/add/remove methods for each, along with the original 30 columns and their methods, and some supporting utility functions then the Person entity is going to be 1000+ lines long and a nightmare to test.
FWIW i plan to create a PersonRepository to handle the common bulk queries, a PersonProfessionRepository for the bulk queries / reports on that sub table etc, and Person*Service s which will contain some of the more complex business logic where needed. So organising the rest of the app logic is fine: this is a question about how to correctly organise lots of sub-table Entities with Doctrine that all have relationships / associations back to one primary table. How do I avoid bloating out the Person entity class?
Identifying types of objects
It sounds like you have a nicely normalized database and I suggest you keep it that way. Removing columns from the people table to create separate tables for one-to-one relations isn't going to help in performance nor maintainability.
The fact that you recognize several groups of properties in the Person entity might indicate you have found cases for a Value Object. Even some of the one-to-many tables (like person_address) sound more like Value Objects than Entities.
Starting with Doctrine 2.5 (which is not yet stable at the time of this writing) it will support embedding single Value Objects. Unfortunately we will have to wait for a future version for support of collections of Value objects.
Putting that aside, you can mimic embedding Value Objects, Ross Tuck has blogged about this.
Lasagna Code
Your plan of implementing an entity, repository, service (and maybe controller?) for Person, PersonProfession, etc sounds like a road to Lasagna Code.
Without extensive knowledge about your domain, I'd say you want to have an aggregate Person, of which the Person entity is the aggregate root. That aggregate needs a single repository. (But maybe I'm off here and being simplistic, as I said, I don't know your domain.)
Creating a service for Person (and other entities / value objects) indicates data-minded thinking. For services it's better to think of behavior. Think of what kind of tasks you want to perform, and group coherent sets of tasks into services. I suspect that for a HR system you'll end up with many services that evolve around your Person aggregate.
Is Doctrine 2 suitable?
I would say: yes. Doctrine itself has no problems with large amounts of tables and large amounts of columns. But performance highly depends on how you use it.
OLTP vs OLAP
For OLTP systems an ORM can be very helpful. OLTP involves many short transactions, writing a single (or short list) of aggregates to the database.
For OLAP systems an ORM is not suited. OLAP involves many complex analytical queries, usually resulting in large object-graphs. For these kind of operations, native SQL is much more convenient.
Even in case of OLAP systems Doctrine 2 can be of help:
You can use DQL queries (in stead of native SQL) to use the power of your mapping metadata. Then use scalar or array hydration to fetch the data.
Doctrine also support arbitrary joins, which means you can join entities that are not associated to each other according by mapping metadata.
And you can make use of the NativeQuery object with which you can map the results to whatever you want.
I think a HR system is a perfect example of where you have both OLTP and OLAP. OLTP when it comes to adding a new Person to the system for example. OLAP when it comes to various reports and analytics.
So there's nothing wrong with using an ORM for transactional operations, while using plain SQL for analytical operations.
Choose wisely
I think the key is to carefully choose when to use what, on a case by case basis.
Hydrating entities is great for transactional operations. Make use of lazy loading associations which can prevent fetching data you're not going to use. But also choose to eager load certain associations (using DQL) where it makes sense.
Use scalar or array hydration when working with large data sets. Data sets usually grow where you're doing analytical operations, where you don't really need full blown entities anyway.
#Quicker makes a valid point by saying you can create specialized View objects. You can fetch only the data you need in specific cases and manually mold that data into objects. This is accompanied by his point to don't bloat the user interface with options a user with a certain role doesn't need.
A technique you might want to look into is Command Query Responsibility Segregation (CQRS).
I understood that you have a fully normalized table persons and now you are asking for how to denormalize that best.
As long as you do not hit any technical constaints (such as max 64 K Byte) I find 70 columns definitly not overloaded for a persons table in a HR system. Do yourself a favour to not segment that information for following reasons:
selects potentially become more complex
each extract table needs (an) extra index/indeces, which increases your overall memory utilization -> this sounds to be a minor issue as disk is cheap. However keep in mind that via caching the RAM to disk space utilization ratio determines your performance to a huge extend
changes become more complex as extra relations demand for extra care
as any edit/update/read view can be restricted to deal with slices of your physical data from the tables only no "cosmetics" pressure arises from end user (or even admin) perspective
In summary your the table subsetting causes lots of issues and effort but does add low if not no value.
Btw. databases are optimized for data storage. Millions of rows and some dozens of columns are no brainers at that end.
TL;DR: should I use an SQL JOIN table or Redis sets to store large amounts of many-to-many relationships
I have in-memory object graph structure where I have a "many-to-many" index represented as a bidirectional mapping between ordered sets:
group_by_user | user_by_group
--------------+---------------
louis: [1,2] | 1: [louis]
john: [2,3] | 2: [john, louis]
| 3: [john]
The basic operations that I need to be able to perform are atomic "insert at" and "delete" operations on the individual sets. I also need to be able to do efficient key lookup (e.g. lookup all groups a user is a member of, or lookup all the users who are members of one group). I am looking at a 70/30 read/write use case.
My question is: what is my best bet for persisting this kind of data structure? Should I be looking at building my own optimized on-disk storage system? Otherwise, is there a particular database that would excel at storing this kind of structure?
Before you read any further: stop being afraid of JOINs. This is a classic case for using a genuine relational database such as Postgres.
There are a few reasons for this:
This is what a real RDBMS is optimized for
The database can take care of your integrity constraints as a matter of course
This is what a real RDBMS is optimized for
You will have to push "join" logic into your own code
This is what a real RDBMS is optimized for
You will have to deal with integrity concerns in your own code
This is what a real RDBMS is optimized for
You will wind up reinventing database features in your own code
This is what a real RDBMS is optimized for
Yes, I am being a little silly, but because I'm trying to drive home a point.
I am beating on that drum so hard because this is a classic case that has a readily available, extremely optimized and profoundly stable tool custom designed for it.
When I say that you will wind up reinventing database features I mean that you will start having to make basic data management decisions in your own code. For example, you will have to choose when to actually write the data to disk, when to pull it, how to keep track of the highest-frequency use data and cache it in memory (and how to manage that cache), etc. Making performance assumptions into your code early can give your whole codebase cancer early on without you noticing it -- and if those assumptions prove false later changing them can require a major rewrite.
If you store the data on either end of the many-to-many relationship in one store and the many-to-many map in another store you will have to:
Locate the initial data on one side of the mapping
Extract the key(s)
Query for the key(s) in the many-to-many handler
Receive the response set(s)
Query whatever is relevant from your other storage based on the result
Build your answer for use within the system
If you structure your data within an RDBMS to begin with your code will look more like:
Run a pre-built query indexed over whatever your search criteria is
Build an answer from the response
JOINs are a lot less scary than doing it all yourself -- especially in a concurrent system where other things may be changing in the course of your ad hoc locate-extract-query-receive-query-build procedure (which can be managed, of course, but why manage it when an RDBMS is already designed to manage it?).
JOIN isn't even a slow operation in decent databases. I have some business applications that join 20 tables constantly over fairly large tables (several millions of rows) and it zips right through them. It is highly optimized for this sort of thing which is why I use it. Oracle does well at this (but I can't afford it), DB2 is awesome (can't afford that, either), and SQL Server has come a long way (can't afford the good version of that one either!). MySQL, on the other hand, was really designed with the key-value store use-case in mind and matured in the "performance above all else" world of web applications -- and so it has some problems with integrity constraints and JOINs (but has handled replication very well for a very long time). So not all RDBMSes are created equal, but without knowing anything else about your problem they are the kind of datastore that will serve you best.
Even slightly non-trivial data can make your code explode in complexity -- hence the popularity of database systems. They aren't (supposed to be) religions, they are tools to let you separate a generic data-handling task from your own program's logic so you don't have to reinvent the wheel every project (but we tend to anyway).
But
Q: When would you not want to do this?
A: When you are really building a graph and not a set of many-to-many relations.
There is other type of database designed specifically to handle that case. You need to keep in mind, though, what your actual requirements are. Is this data ephemeral? Does it have to be correct? Do you care if you lose it? Does it need to be replicated? etc. Most of the time requirements are relatively trivial and the answer is "no" to these sort of higher-flying questions -- but if you have some special operational needs then you may need to take them into account when making your architectural decision.
If you are storing things that are actually documents (instead of structured records) on the one hand, and need to track a graph of relationships among them on the other then a combination of back-ends may be a good idea. A document database + a graphing database glued together by some custom code could be the right thing.
Think carefully about which kind of situation you are actually facing instead of assuming you have case X because it is what you are already familiar with.
In relational databases (e. g. SqlServer, MySql, Oracle...), the typical way of representing such data structures is with a "link table". For example:
users table:
userId (primary key)
userName
...
groups table:
groupId (primary key)
...
userGroups table: (this is the link table)
userId (foreign key to users table)
groupId (foreign key to groups table)
compound primary key of (userId, groupId)
Thus, to find all groups with users named "fred", you might write the following query:
SELECT g.*
FROM users u
JOIN userGroups ug ON ug.userId = u.userId
JOIN groups g ON g.groupId = ug.groupId
WHERE u.name = 'fred'
To achieve atomic inserts, updates, and deletes of this structure, you'll have to execute the queries that modify the various tables in transactions. ORM's such as EntityFramework (for .NET) will typically handle this for you.
The more I read about NoSQL, the more it begins to sound like a column oriented database to me.
What's the difference between NoSQL (e.g. CouchDB, Cassandra, MongoDB) and a column oriented database (e.g. Vertica, MonetDB)?
NoSQL is term used for Not Only SQL, which covers four major categories - Key-Value, Document, Column Family and Graph databases.
Key-value databases are well-suited to applications that have frequent small reads and writes along with simple data models.
These records are stored and retrieved using a key that uniquely identifies the record, and is used to quickly find the data within the database.
e.g. Redis, Riak etc.
Document databases have ability to store varying attributes along with large amounts of data
e.g. MongoDB , CouchDB etc.
Column family databases are designed for large volumes of data, read and write performance, and high availability
e.g Cassandra, HBase etc.
Graph database is a database that uses graph structures for semantic queries with nodes, edges and properties to represent and store data
e.g Neo4j, InfiniteGraph etc.
Before understanding NoSQL, you have to understand some key concepts.
Consistency – All the servers in the system will have the same data so anyone using the system will get the same copy regardless of which server answers their request.
Availability – The system will always respond to a request (even if it's not the latest data or consistent across the system or just a message saying the system isn't working) .
Partition Tolerance – The system continues to operate as a whole even if individual servers fail or can't be reached.
Most of the times, only two out above three properties will be satisfied by NoSQL databases.
From your question,
CouchDB : AP ( Availability & Partition) & Document database
Cassandra : AP ( Availability & Partition) & Column family database
MongoDB : CP ( Consistency & Partition) & Document database
Vertica : CA ( Consistency & Availability) & Column family database
MonetDB : ACID (Atomicity Consistency Isolation Durability) & Relational database
From : http://blog.nahurst.com/visual-guide-to-nosql-systems
Have a look at this article1 , article2 and ppt for various scenarios to select a particular type of database.
Some NoSQL databases are column-oriented databases, and some SQL databases are column-oriented as well. Whether the database is column or row-oriented is a physical storage implementation detail of the database and can be true of both relational and non-relational (NoSQL) databases.
Vertica, for example, is a column-oriented relational database so it wouldn't actually qualify as a NoSQL datastore.
A "NoSQL movement" datastore is better defined as being non-relational, shared-nothing, horizontally scalable database without (necessarily) ACID guarantees. Some column-oriented databases can be characterized this way. Besides column stores, NoSQL implementations also include document stores, object stores, tuple stores, and graph stores.
A NoSQL Database is a different paradigm from traditional schema based databases. They are designed to scale and hold documents like json data. Obviously they have a way of querying information, but you should expect syntax like eval("person = * and age > 10) for retrieving data. Even if they support standard SQL interface, they are intended for something else, so if you like SQL you should stick to traditional databases.
A column-oriented database is different from traditional row-oriented databases because of how they store data. By storing a whole column together instead of a row, you can minimize disk access when selecting a few columns from a row containing many columns. In row-oriented databases there's no difference if you select just one or all fields from a row.
You have to pay for a more expensive insert though. Inserting a new row will cause many disk operations, depending on the number of columns.
But there's no difference with traditional databases in terms of SQL, ACID, foreign keys and stuff like that.
I would suggest reading the taxonomy section of the NoSQL wikipedia entry to get a feel for just how different NoSQL databases are from a traditional schema-oriented database. Being column-oriented implies rows and columns, which implies a (two dimensional) schema, while NoSQL databases tend to be schema-less (key-value stores) or have structured contents but without a formal schema (document stores).
For document stores, the structure and contents of each "document" are independent of other documents in the same "collection". Adding a field is usually a code change rather than a database change: new documents get an entry for the new field, while older documents are considered to have a null value for the non-existent field. Similarly, "removing" a field could mean that you simply stop referring to it in your code rather than going to the trouble of deleting it from each document (unless space is at a premium, and then you have the option of removing only those with the largest contents). Contrast this to how an entire table must be changed to add or remove a column in a traditional row/column database.
Documents can also hold lists as well as other nested documents. Here's a sample document from MongoDB (a post from a blog or other forum), represented as JSON:
{
_id : ObjectId("4e77bb3b8a3e000000004f7a"),
when : Date("2011-09-19T02:10:11.3Z"),
author : "alex",
title : "No Free Lunch",
text : "This is the text of the post. It could be very long.",
tags : [ "business", "ramblings" ],
votes : 5,
voters : [ "jane", "joe", "spencer", "phyllis", "li" ],
comments : [
{ who : "jane", when : Date("2011-09-19T04:00:10.112Z"),
comment : "I agree." },
{ who : "meghan", when : Date("2011-09-20T14:36:06.958Z"),
comment : "You must be joking. etc etc ..." }
]
}
Note how "comments" is a list of nested documents with their own independent structure. Queries can "reach into" these documents from the outer document, for example to find posts that have comments by Jane, or posts with comments from a certain date range.
So in short, two of the major differences typical of NoSQL databases are the lack of a (formal) schema and contents that go beyond the two dimensional orientation of a traditional row/column database.
Distinguishing between coloumn stores Read this blog. This answers your question.
As #tuinstoel wrote, the article answers your question in point 3:
3. Interface. Group A is distinguished by being part of the
NoSQL movement and does not typically
have a traditional SQL interface.
Group B supports standard SQL
interfaces.
Here is how I see it: Column Oriented databases are dealing with the way data is physically stored on disk. As the name suggests, the each column is stored in its own separate space/file. This allows for 2 important things:
You achieve better compression ratio to the order of 10:1 because you have single data type to deal with.
You achieve better data read performance because you avoid whole row scans and can just pick and choose the columns specified in your SELECT query.
NoSQL on the other hand are a whole new breed of databases that define "logical" aggregate levels to explain the data. Some treat the data as having hierachical relationship (aggregate being a "node"), while the other treat the data as documents (which is the aggregate level). They do not dictate the physical storage strategy (some may do, but abstracted away from the end user).
Also, the whole NoSQL movement is more to do with unstructured data, or rather data sets whose schema cannot be predefined, or in unknown beforehand, and therefore cannot conform to the strict relational model.
Column Oriented databases still deal with relational data, although eliminate the need for index etc.